@@ -11,157 +11,159 @@ const awsCredentialsDeprecationNotice = function awsCredentialsDeprecationNotice
1111 'See: https://github.com/parse-server-modules/parse-server-s3-adapter#aws-credentials for details' ) ;
1212} ;
1313
14- // Creates an S3 session.
15- // Providing AWS access, secret keys and bucket are mandatory
16- // Region will use sane defaults if omitted
17- function S3Adapter ( ...args ) {
18- const options = optionsFromArguments ( args ) ;
19- this . _region = options . region ;
20- this . _bucket = options . bucket ;
21- this . _bucketPrefix = options . bucketPrefix ;
22- this . _directAccess = options . directAccess ;
23- this . _baseUrl = options . baseUrl ;
24- this . _baseUrlDirect = options . baseUrlDirect ;
25- this . _signatureVersion = options . signatureVersion ;
26- this . _globalCacheControl = options . globalCacheControl ;
27- this . _encryption = options . ServerSideEncryption ;
14+ class S3Adapter {
15+ // Creates an S3 session.
16+ // Providing AWS access, secret keys and bucket are mandatory
17+ // Region will use sane defaults if omitted
18+ constructor ( ...args ) {
19+ const options = optionsFromArguments ( args ) ;
20+ this . _region = options . region ;
21+ this . _bucket = options . bucket ;
22+ this . _bucketPrefix = options . bucketPrefix ;
23+ this . _directAccess = options . directAccess ;
24+ this . _baseUrl = options . baseUrl ;
25+ this . _baseUrlDirect = options . baseUrlDirect ;
26+ this . _signatureVersion = options . signatureVersion ;
27+ this . _globalCacheControl = options . globalCacheControl ;
28+ this . _encryption = options . ServerSideEncryption ;
2829
29- const s3Options = {
30- params : { Bucket : this . _bucket } ,
31- region : this . _region ,
32- signatureVersion : this . _signatureVersion ,
33- globalCacheControl : this . _globalCacheControl ,
34- } ;
35-
36- if ( options . accessKey && options . secretKey ) {
37- awsCredentialsDeprecationNotice ( ) ;
38- s3Options . accessKeyId = options . accessKey ;
39- s3Options . secretAccessKey = options . secretKey ;
40- }
30+ const s3Options = {
31+ params : { Bucket : this . _bucket } ,
32+ region : this . _region ,
33+ signatureVersion : this . _signatureVersion ,
34+ globalCacheControl : this . _globalCacheControl ,
35+ } ;
4136
42- Object . assign ( s3Options , options . s3overrides ) ;
37+ if ( options . accessKey && options . secretKey ) {
38+ awsCredentialsDeprecationNotice ( ) ;
39+ s3Options . accessKeyId = options . accessKey ;
40+ s3Options . secretAccessKey = options . secretKey ;
41+ }
4342
44- this . _s3Client = new AWS . S3 ( s3Options ) ;
45- this . _hasBucket = false ;
46- }
43+ Object . assign ( s3Options , options . s3overrides ) ;
4744
48- S3Adapter . prototype . createBucket = function ( ) {
49- let promise ;
50- if ( this . _hasBucket ) {
51- promise = Promise . resolve ( ) ;
52- } else {
53- promise = new Promise ( ( resolve ) => {
54- this . _s3Client . createBucket ( ( ) => {
55- this . _hasBucket = true ;
56- resolve ( ) ;
57- } ) ;
58- } ) ;
45+ this . _s3Client = new AWS . S3 ( s3Options ) ;
46+ this . _hasBucket = false ;
5947 }
60- return promise ;
61- } ;
6248
63- // For a given config object, filename, and data, store a file in S3
64- // Returns a promise containing the S3 object creation response
65- S3Adapter . prototype . createFile = function ( filename , data , contentType ) {
66- const params = {
67- Key : this . _bucketPrefix + filename ,
68- Body : data ,
69- } ;
70- if ( this . _directAccess ) {
71- params . ACL = 'public-read' ;
72- }
73- if ( contentType ) {
74- params . ContentType = contentType ;
75- }
76- if ( this . _globalCacheControl ) {
77- params . CacheControl = this . _globalCacheControl ;
78- }
79- if ( this . _encryption === 'AES256' || this . _encryption === 'aws:kms' ) {
80- params . ServerSideEncryption = this . _encryption ;
49+ createBucket ( ) {
50+ let promise ;
51+ if ( this . _hasBucket ) {
52+ promise = Promise . resolve ( ) ;
53+ } else {
54+ promise = new Promise ( ( resolve ) => {
55+ this . _s3Client . createBucket ( ( ) => {
56+ this . _hasBucket = true ;
57+ resolve ( ) ;
58+ } ) ;
59+ } ) ;
60+ }
61+ return promise ;
8162 }
82- return this . createBucket ( ) . then ( ( ) => new Promise ( ( resolve , reject ) => {
83- this . _s3Client . upload ( params , ( err , response ) => {
84- if ( err !== null ) {
85- return reject ( err ) ;
86- }
87- return resolve ( response ) ;
88- } ) ;
89- } ) ) ;
90- } ;
9163
92- S3Adapter . prototype . deleteFile = function ( filename ) {
93- return this . createBucket ( ) . then ( ( ) => new Promise ( ( resolve , reject ) => {
64+ // For a given config object, filename, and data, store a file in S3
65+ // Returns a promise containing the S3 object creation response
66+ createFile ( filename , data , contentType ) {
9467 const params = {
9568 Key : this . _bucketPrefix + filename ,
69+ Body : data ,
9670 } ;
97- this . _s3Client . deleteObject ( params , ( err , data ) => {
98- if ( err !== null ) {
99- return reject ( err ) ;
100- }
101- return resolve ( data ) ;
102- } ) ;
103- } ) ) ;
104- } ;
71+ if ( this . _directAccess ) {
72+ params . ACL = 'public-read' ;
73+ }
74+ if ( contentType ) {
75+ params . ContentType = contentType ;
76+ }
77+ if ( this . _globalCacheControl ) {
78+ params . CacheControl = this . _globalCacheControl ;
79+ }
80+ if ( this . _encryption === 'AES256' || this . _encryption === 'aws:kms' ) {
81+ params . ServerSideEncryption = this . _encryption ;
82+ }
83+ return this . createBucket ( ) . then ( ( ) => new Promise ( ( resolve , reject ) => {
84+ this . _s3Client . upload ( params , ( err , response ) => {
85+ if ( err !== null ) {
86+ return reject ( err ) ;
87+ }
88+ return resolve ( response ) ;
89+ } ) ;
90+ } ) ) ;
91+ }
10592
106- // Search for and return a file if found by filename
107- // Returns a promise that succeeds with the buffer result from S3
108- S3Adapter . prototype . getFileData = function ( filename ) {
109- const params = { Key : this . _bucketPrefix + filename } ;
110- return this . createBucket ( ) . then ( ( ) => new Promise ( ( resolve , reject ) => {
111- this . _s3Client . getObject ( params , ( err , data ) => {
112- if ( err !== null ) {
113- return reject ( err ) ;
114- }
115- // Something happened here...
116- if ( data && ! data . Body ) {
117- return reject ( data ) ;
118- }
119- return resolve ( data . Body ) ;
120- } ) ;
121- } ) ) ;
122- } ;
93+ deleteFile ( filename ) {
94+ return this . createBucket ( ) . then ( ( ) => new Promise ( ( resolve , reject ) => {
95+ const params = {
96+ Key : this . _bucketPrefix + filename ,
97+ } ;
98+ this . _s3Client . deleteObject ( params , ( err , data ) => {
99+ if ( err !== null ) {
100+ return reject ( err ) ;
101+ }
102+ return resolve ( data ) ;
103+ } ) ;
104+ } ) ) ;
105+ }
123106
124- // Generates and returns the location of a file stored in S3 for the given request and filename
125- // The location is the direct S3 link if the option is set,
126- // otherwise we serve the file through parse-server
127- S3Adapter . prototype . getFileLocation = function ( config , filename ) {
128- const fileName = encodeURIComponent ( filename ) ;
129- if ( this . _directAccess ) {
130- if ( this . _baseUrl && this . _baseUrlDirect ) {
131- return `${ this . _baseUrl } /${ fileName } ` ;
132- } if ( this . _baseUrl ) {
133- return `${ this . _baseUrl } /${ this . _bucketPrefix + fileName } ` ;
134- }
135- return `https://${ this . _bucket } .s3.amazonaws.com/${ this . _bucketPrefix + fileName } ` ;
107+ // Search for and return a file if found by filename
108+ // Returns a promise that succeeds with the buffer result from S3
109+ getFileData ( filename ) {
110+ const params = { Key : this . _bucketPrefix + filename } ;
111+ return this . createBucket ( ) . then ( ( ) => new Promise ( ( resolve , reject ) => {
112+ this . _s3Client . getObject ( params , ( err , data ) => {
113+ if ( err !== null ) {
114+ return reject ( err ) ;
115+ }
116+ // Something happened here...
117+ if ( data && ! data . Body ) {
118+ return reject ( data ) ;
119+ }
120+ return resolve ( data . Body ) ;
121+ } ) ;
122+ } ) ) ;
136123 }
137- return ( `${ config . mount } /files/${ config . applicationId } /${ fileName } ` ) ;
138- } ;
139124
140- S3Adapter . prototype . handleFileStream = function ( filename , req , res ) {
141- const params = {
142- Key : this . _bucketPrefix + filename ,
143- Range : req . get ( 'Range' ) ,
144- } ;
145- return this . createBucket ( ) . then ( ( ) => new Promise ( ( resolve , reject ) => {
146- this . _s3Client . getObject ( params , ( error , data ) => {
147- if ( error !== null ) {
148- return reject ( error ) ;
125+ // Generates and returns the location of a file stored in S3 for the given request and filename
126+ // The location is the direct S3 link if the option is set,
127+ // otherwise we serve the file through parse-server
128+ getFileLocation ( config , filename ) {
129+ const fileName = encodeURIComponent ( filename ) ;
130+ if ( this . _directAccess ) {
131+ if ( this . _baseUrl && this . _baseUrlDirect ) {
132+ return `${ this . _baseUrl } /${ fileName } ` ;
133+ } if ( this . _baseUrl ) {
134+ return `${ this . _baseUrl } /${ this . _bucketPrefix + fileName } ` ;
149135 }
150- if ( data && ! data . Body ) {
151- return reject ( data ) ;
152- }
153- res . writeHead ( 206 , {
154- 'Accept-Ranges' : data . AcceptRanges ,
155- 'Content-Length' : data . ContentLength ,
156- 'Content-Range' : data . ContentRange ,
157- 'Content-Type' : data . ContentType ,
136+ return `https://${ this . _bucket } .s3.amazonaws.com/${ this . _bucketPrefix + fileName } ` ;
137+ }
138+ return ( `${ config . mount } /files/${ config . applicationId } /${ fileName } ` ) ;
139+ }
140+
141+ handleFileStream ( filename , req , res ) {
142+ const params = {
143+ Key : this . _bucketPrefix + filename ,
144+ Range : req . get ( 'Range' ) ,
145+ } ;
146+ return this . createBucket ( ) . then ( ( ) => new Promise ( ( resolve , reject ) => {
147+ this . _s3Client . getObject ( params , ( error , data ) => {
148+ if ( error !== null ) {
149+ return reject ( error ) ;
150+ }
151+ if ( data && ! data . Body ) {
152+ return reject ( data ) ;
153+ }
154+ res . writeHead ( 206 , {
155+ 'Accept-Ranges' : data . AcceptRanges ,
156+ 'Content-Length' : data . ContentLength ,
157+ 'Content-Range' : data . ContentRange ,
158+ 'Content-Type' : data . ContentType ,
159+ } ) ;
160+ res . write ( data . Body ) ;
161+ res . end ( ) ;
162+ return resolve ( data . Body ) ;
158163 } ) ;
159- res . write ( data . Body ) ;
160- res . end ( ) ;
161- return resolve ( data . Body ) ;
162- } ) ;
163- } ) ) ;
164- } ;
164+ } ) ) ;
165+ }
166+ }
165167
166168module . exports = S3Adapter ;
167169module . exports . default = S3Adapter ;
0 commit comments