mirror of
				https://github.com/actions/cache.git
				synced 2025-11-04 23:58:41 +08:00 
			
		
		
		
	Merge pull request #1 from whywaita/support-s3
Support AWS S3 and compatible software
This commit is contained in:
		
						commit
						c901222582
					
				
							
								
								
									
										29
									
								
								README.md
									
									
									
									
									
								
							
							
						
						
									
										29
									
								
								README.md
									
									
									
									
									
								
							| 
						 | 
					@ -1,3 +1,32 @@
 | 
				
			||||||
 | 
					# whywaita/actions-cache-s3
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					`whywaita/actions-cache-s3` is a forked Action from [@actions/cache](https://github.com/actions/cache).
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					This Action provides Amazon Web Services S3 backend (and compatible software) for @actions/cache.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					## Usage
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					```yaml
 | 
				
			||||||
 | 
					- name: Cache multiple paths
 | 
				
			||||||
 | 
					  uses: whywaita/actions-cache-s3@main
 | 
				
			||||||
 | 
					  with:
 | 
				
			||||||
 | 
					    path: |
 | 
				
			||||||
 | 
					      ~/cache
 | 
				
			||||||
 | 
					      !~/cache/exclude
 | 
				
			||||||
 | 
					    key: ${{ runner.os }}-${{ hashFiles('**/lockfiles') }}
 | 
				
			||||||
 | 
					    restore-keys: |
 | 
				
			||||||
 | 
					      ${{ runner.os }}-go-
 | 
				
			||||||
 | 
					    aws-s3-bucket: ${{ secrets.AWS_S3_BUCKET_NAME }}
 | 
				
			||||||
 | 
					    aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
 | 
				
			||||||
 | 
					    aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
 | 
				
			||||||
 | 
					    aws-region: us-east-1                      # Optional
 | 
				
			||||||
 | 
					    aws-endpoint: https://example.com          # Optional
 | 
				
			||||||
 | 
					    aws-s3-bucket-endpoint: false              # Optional
 | 
				
			||||||
 | 
					    aws-s3-force-path-style: true              # Optional
 | 
				
			||||||
 | 
					```
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					Please see [actions.yml](https://github.com/whywaita/actions-cache-s3/blob/main/action.yml) about input parameters.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
# cache
 | 
					# cache
 | 
				
			||||||
 | 
					
 | 
				
			||||||
This action allows caching dependencies and build outputs to improve workflow execution time.
 | 
					This action allows caching dependencies and build outputs to improve workflow execution time.
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
							
								
								
									
										23
									
								
								action.yml
									
									
									
									
									
								
							
							
						
						
									
										23
									
								
								action.yml
									
									
									
									
									
								
							| 
						 | 
					@ -14,6 +14,29 @@ inputs:
 | 
				
			||||||
  upload-chunk-size:
 | 
					  upload-chunk-size:
 | 
				
			||||||
    description: 'The chunk size used to split up large files during upload, in bytes'
 | 
					    description: 'The chunk size used to split up large files during upload, in bytes'
 | 
				
			||||||
    required: false
 | 
					    required: false
 | 
				
			||||||
 | 
					  aws-s3-bucket:
 | 
				
			||||||
 | 
					    description: 'An AWS S3 bucket to save cache'
 | 
				
			||||||
 | 
					    required: true
 | 
				
			||||||
 | 
					  aws-access-key-id:
 | 
				
			||||||
 | 
					    description: 'An AWS access key id to access the bucket'
 | 
				
			||||||
 | 
					    required: true
 | 
				
			||||||
 | 
					  aws-secret-access-key:
 | 
				
			||||||
 | 
					    description: 'An AWS secret access key to access the bucket'
 | 
				
			||||||
 | 
					    required: true
 | 
				
			||||||
 | 
					  aws-region:
 | 
				
			||||||
 | 
					    description: 'An AWS region where the bucket is located'
 | 
				
			||||||
 | 
					    required: false
 | 
				
			||||||
 | 
					  aws-endpoint:
 | 
				
			||||||
 | 
					    description: 'An endpoint of AWS S3 (for compatible software)'
 | 
				
			||||||
 | 
					    required: false
 | 
				
			||||||
 | 
					  aws-s3-bucket-endpoint:
 | 
				
			||||||
 | 
					    description: 'Whether to use the bucket name as the endpoint for this request.'
 | 
				
			||||||
 | 
					    required: false
 | 
				
			||||||
 | 
					    default: true
 | 
				
			||||||
 | 
					  aws-s3-force-path-style:
 | 
				
			||||||
 | 
					    description: 'Whether to force path style URLs for S3 objects.'
 | 
				
			||||||
 | 
					    required: false
 | 
				
			||||||
 | 
					    default: false
 | 
				
			||||||
outputs:
 | 
					outputs:
 | 
				
			||||||
  cache-hit:
 | 
					  cache-hit:
 | 
				
			||||||
    description: 'A boolean value to indicate an exact match was found for the primary key'
 | 
					    description: 'A boolean value to indicate an exact match was found for the primary key'
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
							
								
								
									
										73655
									
								
								dist/restore/index.js
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										73655
									
								
								dist/restore/index.js
									
									
									
									
										vendored
									
									
								
							
										
											
												File diff suppressed because one or more lines are too long
											
										
									
								
							
							
								
								
									
										73652
									
								
								dist/save/index.js
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										73652
									
								
								dist/save/index.js
									
									
									
									
										vendored
									
									
								
							
										
											
												File diff suppressed because one or more lines are too long
											
										
									
								
							
							
								
								
									
										1503
									
								
								package-lock.json
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										1503
									
								
								package-lock.json
									
									
									
										generated
									
									
									
								
							
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							| 
						 | 
					@ -23,10 +23,12 @@
 | 
				
			||||||
  "author": "GitHub",
 | 
					  "author": "GitHub",
 | 
				
			||||||
  "license": "MIT",
 | 
					  "license": "MIT",
 | 
				
			||||||
  "dependencies": {
 | 
					  "dependencies": {
 | 
				
			||||||
    "@actions/cache": "^1.0.9",
 | 
					    "@actions/cache": "https://gitpkg.now.sh/whywaita/toolkit/packages/cache?main",
 | 
				
			||||||
    "@actions/core": "^1.2.6",
 | 
					    "@actions/core": "^1.2.6",
 | 
				
			||||||
    "@actions/exec": "^1.0.1",
 | 
					    "@actions/exec": "^1.0.1",
 | 
				
			||||||
    "@actions/io": "^1.1.0"
 | 
					    "@actions/io": "^1.1.0",
 | 
				
			||||||
 | 
					    "@aws-sdk/client-s3": "^3.51.0",
 | 
				
			||||||
 | 
					    "@aws-sdk/types": "^3.50.0"
 | 
				
			||||||
  },
 | 
					  },
 | 
				
			||||||
  "devDependencies": {
 | 
					  "devDependencies": {
 | 
				
			||||||
    "@types/jest": "^27.4.0",
 | 
					    "@types/jest": "^27.4.0",
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -2,7 +2,14 @@ export enum Inputs {
 | 
				
			||||||
    Key = "key",
 | 
					    Key = "key",
 | 
				
			||||||
    Path = "path",
 | 
					    Path = "path",
 | 
				
			||||||
    RestoreKeys = "restore-keys",
 | 
					    RestoreKeys = "restore-keys",
 | 
				
			||||||
    UploadChunkSize = "upload-chunk-size"
 | 
					    UploadChunkSize = "upload-chunk-size",
 | 
				
			||||||
 | 
					    AWSS3Bucket = "aws-s3-bucket",
 | 
				
			||||||
 | 
					    AWSAccessKeyId = "aws-access-key-id",
 | 
				
			||||||
 | 
					    AWSSecretAccessKey = "aws-secret-access-key",
 | 
				
			||||||
 | 
					    AWSRegion = "aws-region",
 | 
				
			||||||
 | 
					    AWSEndpoint = "aws-endpoint",
 | 
				
			||||||
 | 
					    AWSS3BucketEndpoint = "aws-s3-bucket-endpoint",
 | 
				
			||||||
 | 
					    AWSS3ForcePathStyle = "aws-s3-force-path-style"
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export enum Outputs {
 | 
					export enum Outputs {
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -6,14 +6,6 @@ import * as utils from "./utils/actionUtils";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
async function run(): Promise<void> {
 | 
					async function run(): Promise<void> {
 | 
				
			||||||
    try {
 | 
					    try {
 | 
				
			||||||
        if (utils.isGhes()) {
 | 
					 | 
				
			||||||
            utils.logWarning(
 | 
					 | 
				
			||||||
                "Cache action is not supported on GHES. See https://github.com/actions/cache/issues/505 for more details"
 | 
					 | 
				
			||||||
            );
 | 
					 | 
				
			||||||
            utils.setCacheHitOutput(false);
 | 
					 | 
				
			||||||
            return;
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        // Validate inputs, this can cause task failure
 | 
					        // Validate inputs, this can cause task failure
 | 
				
			||||||
        if (!utils.isValidEvent()) {
 | 
					        if (!utils.isValidEvent()) {
 | 
				
			||||||
            utils.logWarning(
 | 
					            utils.logWarning(
 | 
				
			||||||
| 
						 | 
					@ -31,12 +23,17 @@ async function run(): Promise<void> {
 | 
				
			||||||
        const cachePaths = utils.getInputAsArray(Inputs.Path, {
 | 
					        const cachePaths = utils.getInputAsArray(Inputs.Path, {
 | 
				
			||||||
            required: true
 | 
					            required: true
 | 
				
			||||||
        });
 | 
					        });
 | 
				
			||||||
 | 
					        const s3BucketName = core.getInput(Inputs.AWSS3Bucket);
 | 
				
			||||||
 | 
					        const s3config = utils.getInputS3ClientConfig();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        try {
 | 
					        try {
 | 
				
			||||||
            const cacheKey = await cache.restoreCache(
 | 
					            const cacheKey = await cache.restoreCache(
 | 
				
			||||||
                cachePaths,
 | 
					                cachePaths,
 | 
				
			||||||
                primaryKey,
 | 
					                primaryKey,
 | 
				
			||||||
                restoreKeys
 | 
					                restoreKeys,
 | 
				
			||||||
 | 
					                undefined,
 | 
				
			||||||
 | 
					                s3config,
 | 
				
			||||||
 | 
					                s3BucketName
 | 
				
			||||||
            );
 | 
					            );
 | 
				
			||||||
            if (!cacheKey) {
 | 
					            if (!cacheKey) {
 | 
				
			||||||
                core.info(
 | 
					                core.info(
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
							
								
								
									
										11
									
								
								src/save.ts
									
									
									
									
									
								
							
							
						
						
									
										11
									
								
								src/save.ts
									
									
									
									
									
								
							| 
						 | 
					@ -11,13 +11,6 @@ process.on("uncaughtException", e => utils.logWarning(e.message));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
async function run(): Promise<void> {
 | 
					async function run(): Promise<void> {
 | 
				
			||||||
    try {
 | 
					    try {
 | 
				
			||||||
        if (utils.isGhes()) {
 | 
					 | 
				
			||||||
            utils.logWarning(
 | 
					 | 
				
			||||||
                "Cache action is not supported on GHES. See https://github.com/actions/cache/issues/505 for more details"
 | 
					 | 
				
			||||||
            );
 | 
					 | 
				
			||||||
            return;
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        if (!utils.isValidEvent()) {
 | 
					        if (!utils.isValidEvent()) {
 | 
				
			||||||
            utils.logWarning(
 | 
					            utils.logWarning(
 | 
				
			||||||
                `Event Validation Error: The event type ${
 | 
					                `Event Validation Error: The event type ${
 | 
				
			||||||
| 
						 | 
					@ -46,11 +39,13 @@ async function run(): Promise<void> {
 | 
				
			||||||
        const cachePaths = utils.getInputAsArray(Inputs.Path, {
 | 
					        const cachePaths = utils.getInputAsArray(Inputs.Path, {
 | 
				
			||||||
            required: true
 | 
					            required: true
 | 
				
			||||||
        });
 | 
					        });
 | 
				
			||||||
 | 
					        const s3BucketName = core.getInput(Inputs.AWSS3Bucket);
 | 
				
			||||||
 | 
					        const s3config = utils.getInputS3ClientConfig();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        try {
 | 
					        try {
 | 
				
			||||||
            await cache.saveCache(cachePaths, primaryKey, {
 | 
					            await cache.saveCache(cachePaths, primaryKey, {
 | 
				
			||||||
                uploadChunkSize: utils.getInputAsInt(Inputs.UploadChunkSize)
 | 
					                uploadChunkSize: utils.getInputAsInt(Inputs.UploadChunkSize)
 | 
				
			||||||
            });
 | 
					            }, s3config, s3BucketName);
 | 
				
			||||||
            core.info(`Cache saved with key: ${primaryKey}`);
 | 
					            core.info(`Cache saved with key: ${primaryKey}`);
 | 
				
			||||||
        } catch (error) {
 | 
					        } catch (error) {
 | 
				
			||||||
            if (error.name === cache.ValidationError.name) {
 | 
					            if (error.name === cache.ValidationError.name) {
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -1,6 +1,8 @@
 | 
				
			||||||
import * as core from "@actions/core";
 | 
					import * as core from "@actions/core";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import { Outputs, RefKey, State } from "../constants";
 | 
					import { Inputs, Outputs, RefKey, State } from "../constants";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					import {CommonPrefix, InputSerialization, S3ClientConfig} from "@aws-sdk/client-s3";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export function isGhes(): boolean {
 | 
					export function isGhes(): boolean {
 | 
				
			||||||
    const ghUrl = new URL(
 | 
					    const ghUrl = new URL(
 | 
				
			||||||
| 
						 | 
					@ -74,3 +76,25 @@ export function getInputAsInt(
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
    return value;
 | 
					    return value;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					export function getInputS3ClientConfig(): S3ClientConfig | undefined {
 | 
				
			||||||
 | 
					    const s3BucketName = core.getInput(Inputs.AWSS3Bucket)
 | 
				
			||||||
 | 
					    if (!s3BucketName) {
 | 
				
			||||||
 | 
					        return undefined
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    const s3config = {
 | 
				
			||||||
 | 
					        credentials: {
 | 
				
			||||||
 | 
					          accessKeyId: core.getInput(Inputs.AWSAccessKeyId),
 | 
				
			||||||
 | 
					          secretAccessKey: core.getInput(Inputs.AWSSecretAccessKey)
 | 
				
			||||||
 | 
					        },
 | 
				
			||||||
 | 
					        region: core.getInput(Inputs.AWSRegion),
 | 
				
			||||||
 | 
					        endpoint: core.getInput(Inputs.AWSEndpoint),
 | 
				
			||||||
 | 
					        bucketEndpoint: core.getBooleanInput(Inputs.AWSS3BucketEndpoint),
 | 
				
			||||||
 | 
					        forcePathStyle: core.getBooleanInput(Inputs.AWSS3ForcePathStyle),
 | 
				
			||||||
 | 
					    } as S3ClientConfig
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    core.debug('Enable S3 backend mode.')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    return s3config
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
		Reference in New Issue
	
	Block a user