@@ -7,6 +7,7 @@ const withV4 = require('../support/withV4');
77const BucketUtility = require ( '../../lib/utility/bucket-util' ) ;
88const { config, serverAccessLogsModes } = require ( '../../../../../lib/Config' ) ;
99const { methodRequest } = require ( '../../lib/utility/cors-util' ) ;
10+ const { makeRequest } = require ( '../../../raw-node/utils/makeRequest' ) ;
1011
1112const TEST_CONFIG = {
1213 MAX_LOG_WAIT_RETRIES : 50 ,
@@ -98,7 +99,8 @@ var bu;
9899// - [ ] Cloudserver returns PutBucketNotification action for PutBucketNotificationConfiguration (same for the Get)
99100// - We skip QUOTA methods because they are not part of the AWS API.
100101// - We skip objectRestore because it is not supported in CloudServer.
101- describe ( 'Server Access Logs - File Output' , async ( ) => {
102+ // eslint-disable-next-line mocha/no-exclusive-tests
103+ describe . only ( 'Server Access Logs - File Output' , async ( ) => {
102104 withV4 ( async sigCfg => {
103105 const bucketUtil = new BucketUtility ( 'default' , sigCfg ) ;
104106 bu = bucketUtil ;
@@ -558,6 +560,142 @@ describe('Server Access Logs - File Output', async () => {
558560 ] ,
559561 } ;
560562 } ) ( ) ,
563+ ( ( ) => {
564+ // This operation tests website GET and HEAD requests.
565+ const method = async ( ) => {
566+ await s3 . createBucket ( { Bucket : bucketName } ) . promise ( ) ;
567+ // Configure website
568+ await s3 . putBucketWebsite ( {
569+ Bucket : bucketName ,
570+ WebsiteConfiguration : {
571+ IndexDocument : { Suffix : 'index.html' } ,
572+ } ,
573+ } ) . promise ( ) ;
574+ // Add bucket policy to allow public read access for website
575+ await s3 . putBucketPolicy ( {
576+ Bucket : bucketName ,
577+ Policy : JSON . stringify ( {
578+ Version : '2012-10-17' ,
579+ Statement : [ {
580+ Sid : 'PublicReadGetObject' ,
581+ Effect : 'Allow' ,
582+ Principal : '*' ,
583+ Action : [ 's3:GetObject' ] ,
584+ Resource : [
585+ `arn:aws:s3:::${ bucketName } /*` ,
586+ ] ,
587+ } ] ,
588+ } ) ,
589+ } ) . promise ( ) ;
590+ // Put an object to serve via website
591+ await s3 . putObject ( {
592+ Bucket : bucketName ,
593+ Key : 'index.html' ,
594+ Body : '<html><body>Test</body></html>' ,
595+ } ) . promise ( ) ;
596+ // Make a GET request to the website endpoint
597+ // Use makeRequest with Host header so we connect to localhost with path /index.html
598+ // (works without /etc/hosts; cloudserver routes by Host for website)
599+ const websiteHostname = process . env . S3_END_TO_END ?
600+ `${ bucketName } .s3-website-us-east-1.scality.com` :
601+ `${ bucketName } .s3-website-us-east-1.amazonaws.com` ;
602+ const requestHostname = process . env . AWS_ON_AIR ? 's3.amazonaws.com' :
603+ ( process . env . IP || '127.0.0.1' ) ;
604+ const requestPort = process . env . AWS_ON_AIR ? 80 : 8000 ;
605+ await new Promise ( ( resolve , reject ) => {
606+ makeRequest ( {
607+ hostname : requestHostname ,
608+ port : requestPort ,
609+ method : 'GET' ,
610+ path : '/index.html' ,
611+ headers : {
612+ 'Host' : websiteHostname ,
613+ } ,
614+ } , ( err , data ) => {
615+ if ( err ) {
616+ return reject ( err ) ;
617+ }
618+ assert . strictEqual ( data . statusCode , 200 ,
619+ `Expected 200, got ${ data . statusCode } ` ) ;
620+ return resolve ( ) ;
621+ } ) ;
622+ } ) ;
623+ // Make a HEAD request to the website endpoint
624+ await new Promise ( ( resolve , reject ) => {
625+ makeRequest ( {
626+ hostname : requestHostname ,
627+ port : requestPort ,
628+ method : 'HEAD' ,
629+ path : '/index.html' ,
630+ headers : {
631+ 'Host' : websiteHostname ,
632+ } ,
633+ } , ( err , data ) => {
634+ if ( err ) {
635+ return reject ( err ) ;
636+ }
637+ assert . strictEqual ( data . statusCode , 200 ,
638+ `Expected 200, got ${ data . statusCode } ` ) ;
639+ return resolve ( ) ;
640+ } ) ;
641+ } ) ;
642+ } ;
643+ return {
644+ method,
645+ methodName : 'websiteGetHead' ,
646+ expected : [
647+ {
648+ ...commonProperties ,
649+ operation : 'REST.PUT.BUCKET' ,
650+ bucketOwner : null ,
651+ action : 'CreateBucket' ,
652+ httpMethod : 'PUT' ,
653+ } ,
654+ {
655+ ...commonProperties ,
656+ operation : 'REST.PUT.WEBSITE' ,
657+ action : 'PutBucketWebsite' ,
658+ httpMethod : 'PUT' ,
659+ } ,
660+ {
661+ ...commonProperties ,
662+ operation : 'REST.PUT.BUCKETPOLICY' ,
663+ action : 'PutBucketPolicy' ,
664+ httpMethod : 'PUT' ,
665+ } ,
666+ {
667+ ...commonProperties ,
668+ operation : 'REST.PUT.OBJECT' ,
669+ action : 'PutObject' ,
670+ objectKey : 'index.html' ,
671+ httpMethod : 'PUT' ,
672+ } ,
673+ // website[Get|Head]: not in monitoring map, no auth for public website requests
674+ {
675+ ...commonProperties ,
676+ operation : 'WEBSITE.GET.OBJECT' ,
677+ action : undefined ,
678+ accountName : undefined ,
679+ requester : undefined ,
680+ signatureVersion : undefined ,
681+ authenticationType : undefined ,
682+ objectKey : 'index.html' ,
683+ httpMethod : 'GET' ,
684+ } ,
685+ {
686+ ...commonProperties ,
687+ operation : 'WEBSITE.HEAD.OBJECT' ,
688+ action : undefined ,
689+ accountName : undefined ,
690+ requester : undefined ,
691+ signatureVersion : undefined ,
692+ authenticationType : undefined ,
693+ objectKey : 'index.html' ,
694+ httpMethod : 'HEAD' ,
695+ }
696+ ] ,
697+ } ;
698+ } ) ( ) ,
561699 ( ( ) => {
562700 // This operation tests getting a bucket's location.
563701 const method = async ( ) => {
0 commit comments