S3 presigned URL yra laikina nuoroda į vieną objektą privačiame bucket. Jos užklausos eilutėje yra parašas, todėl ją turintis asmuo gali atsisiųsti (ar įkelti) tą objektą be AWS prisijungimo duomenų, kol nuoroda nustos galioti, o bucket niekada netampa viešas. Ją sukuriate savo raktais, savo kode ar per AWS CLI, ir ji gali galioti nuo 1 sekundės iki 7 dienų. Šiame vadove aptariama, kaip tai veikia, ką reiškia kiekvienas X-Amz-* parametras, kiek ilgai nuoroda gali galioti, atsisiuntimų ir įkėlimų kodas ir klaidos, su kuriomis greičiausiai susidursite. Ribos paimtos iš AWS ir Cloudflare dokumentacijos, 2026 m. spalio mėnesio būklė.
S3 presigned URL trumpai
| Klausimas | Atsakymas |
|---|---|
| Ką ji suteikia? | Vieną operaciją (GET, PUT, HEAD, DELETE…) su vienu objektu |
| Didžiausias galiojimas | 7 dienos (604 800 sekundžių) su SigV4 ir IAM vartotojo raktais |
| Galiojimas su laikinais raktais | Baigiasi, kai baigiasi vaidmens sesija ar STS duomenys, kas įvyksta anksčiau |
| S3 konsolės intervalas | Nuo 1 minutės iki 12 valandų |
| Numatytasis galiojimas | 3 600 s AWS CLI ir boto3, 900 s JavaScript v3 presigner |
| Ar galima naudoti kelis kartus? | Taip, kiek tik kas nori, kol ji nustos galioti |
| Ar galima atšaukti vieną URL? | Ne, tik atšaukus pasirašymo duomenis arba uždraudus politikoje |
| Ar jos sukūrimas kreipiasi į S3? | Ne, parašas apskaičiuojamas vietoje |
Kaip veikia presigned URL
- Jūsų kodas (ar CLI) paima bucket, objekto raktą, HTTP metodą ir galiojimo laiką.
- SDK pasirašo šias reikšmes jūsų slaptuoju prieigos raktu naudodamas AWS Signature Version 4. Šiame etape į S3 nieko nesiunčiama.
- Gautą URL kam nors perduodate: naršyklei, kolegai, mobiliajai programai.
- Kai jis panaudojamas, S3 iš naujo apskaičiuoja parašą su slaptuoju raktu, priklausančiu URL nurodytam prieigos raktui. Jei jis sutampa, URL dar galioja, o pasirašiusysis turi teisę atlikti tą operaciją, užklausa įvykdoma.
URL turi jį pasirašiusiojo teises. AWS tai aiškiai nurodo: jei URL sugeneravęs IAM vartotojas ar vaidmuo negali skaityti objekto, URL grąžina 403, kad ir koks galiojantis būtų parašas.
Ką reiškia X-Amz parametrai
SigV4 presigned URL atrodo taip (pridėti eilučių lūžiai):
https://my-bucket.s3.eu-west-1.amazonaws.com/reports/q3.pdf
?X-Amz-Algorithm=AWS4-HMAC-SHA256
&X-Amz-Credential=AKIAIOSFODNN7EXAMPLE%2F20261017%2Feu-west-1%2Fs3%2Faws4_request
&X-Amz-Date=20261017T093000Z
&X-Amz-Expires=3600
&X-Amz-SignedHeaders=host
&X-Amz-Signature=5f2c...e91a
| Parametras | Reikšmė |
|---|---|
X-Amz-Algorithm | Pasirašymo algoritmas: AWS4-HMAC-SHA256 SigV4 atveju |
X-Amz-Credential | Prieigos rakto ID plius apimtis: <key-id>/<YYYYMMDD>/<region>/s3/aws4_request |
X-Amz-Date | Kada URL pasirašytas, UTC laiku, yyyyMMddTHHmmssZ |
X-Amz-Expires | Kiek sekundžių URL galioja po X-Amz-Date, nuo 1 iki 604800 |
X-Amz-SignedHeaders | Parašo apimamos antraštės, visada bent host |
X-Amz-Signature | Parašas, 64 šešioliktainiai simboliai |
X-Amz-Security-Token | Yra tik tada, kai URL pasirašytas laikinais prisijungimo duomenimis (STS, vaidmenys, EC2, ECS, SSO) |
Pakeiskite bet kurią pasirašytą dalį (raktą, metodą, galiojimą ar pasirašytą antraštę), ir parašas nebesutaps. Atkreipkite dėmesį ir į tai, ką URL atskleidžia atviru tekstu: bucket pavadinimą, visą objekto raktą ir jūsų prieigos rakto ID. Slaptojo rakto URL niekada nėra.
Kiek ilgai galioja presigned URL
Riba priklauso nuo jį pasirašančių prisijungimo duomenų:
| Pasirašyta su | Didžiausias galiojimas |
|---|---|
| IAM vartotojo prieigos raktais (SigV4) | 7 dienos, nes pats SigV4 pasirašymo raktas galioja 7 dienas |
| IAM vaidmens sesija (STS AssumeRole) | Kol baigiasi sesija, pagal numatytuosius nustatymus 1 valanda |
| EC2 instance profile | Kol pasikeičia vaidmens duomenys, daugiausia apie 6 valandas |
| ECS užduoties vaidmuo | Kol pasikeičia užduoties duomenys, paprastai kas nuo 1 iki 6 valandų |
| Bet kokie atšaukti ar ištrinti duomenys | Nustoja veikti iš karto, kad ir ką rodytų X-Amz-Expires |
| S3 konsolė | Pasirenkate nuo 1 minutės iki 12 valandų |
Tai paaiškina dažniausią staigmeną: iš Lambda funkcijos ar EC2 egzemplioriaus prašote 7 dienų, o nuoroda nustoja veikti po valandos ar kelių. URL galioja tik tiek, kiek už jo stovintys prisijungimo duomenys. Jei reikia ilgai galiojančių nuorodų, pasirašykite specialiu IAM vartotoju, kuris turi skaitymo prieigą tik prie to bucket.
S3 galiojimą tikrina, kai užklausa prasideda. Didelis atsisiuntimas, prasidėjęs sekundę prieš terminą, baigiamas įprastai, bet pakartotinis bandymas po termino nepavyksta su AccessDenied ir pranešimu „Request has expired“. Prašymas, viršijantis 604 800 sekundžių, atmetamas iš karto.
Kaip sugeneruoti presigned URL
AWS CLI
aws s3 presign s3://my-bucket/reports/q3.pdf --expires-in 3600
Komanda pasirašo atsisiuntimo (GET) URL. Numatytoji reikšmė 3 600 sekundžių, didžiausia 604 800. Naujesnės CLI versijos visada naudoja SigV4, todėl įsitikinkite, kad sukonfigūruotas regionas. Įkėlimo URL reikia SDK.
Python (boto3)
import boto3
from botocore.config import Config
s3 = boto3.client('s3', region_name='eu-west-1', config=Config(signature_version='s3v4'))
url = s3.generate_presigned_url(
ClientMethod='get_object',
Params={
'Bucket': 'my-bucket',
'Key': 'reports/q3.pdf',
'ResponseContentDisposition': 'attachment; filename="q3.pdf"',
},
ExpiresIn=3600,
)
Aiškiai nustatykite signature_version='s3v4'. Boto3 žinyne įspėjama, kad dėl atgalinio suderinamumo kitaip jis gali pasirašyti senesniu Signature Version 2 regionuose, kurie jį dar priima, o tai tyliai pašalina kai kuriuos parametrus ir antraštes, pavyzdžiui, Range. ResponseContentDisposition neprivalomas: jis priverčia naršyklę išsaugoti failą su tvarkingu pavadinimu, užuot atidarius jį naršyklėje.
JavaScript (AWS SDK v3)
import { S3Client, GetObjectCommand } from '@aws-sdk/client-s3'
import { getSignedUrl } from '@aws-sdk/s3-request-presigner'
const client = new S3Client({ region: 'eu-west-1' })
const url = await getSignedUrl(
client,
new GetObjectCommand({ Bucket: 'my-bucket', Key: 'reports/q3.pdf' }),
{ expiresIn: 3600 }
)
Jei praleisite expiresIn, JavaScript presigner naudoja 900 sekundžių (15 minučių).
Presigned įkėlimo URL (PUT)
Ta pati idėja veikia ir priešinga kryptimi. Pasirašote PutObject vienam raktui, ir kas turi URL, gali įrašyti tą objektą. Failas keliauja tiesiai iš jų įrenginio į bucket, o jūsų serveris baitų niekada neapdoroja. Jei objektas su tuo raktu jau yra, jis pakeičiamas.
import { S3Client, PutObjectCommand } from '@aws-sdk/client-s3'
import { getSignedUrl } from '@aws-sdk/s3-request-presigner'
const client = new S3Client({ region: 'eu-west-1' })
const url = await getSignedUrl(
client,
new PutObjectCommand({
Bucket: 'my-bucket',
Key: 'incoming/brief.pdf',
ContentType: 'application/pdf',
}),
{ expiresIn: 900, signableHeaders: new Set(['content-type']) }
)
await fetch(url, {
method: 'PUT',
headers: { 'Content-Type': 'application/pdf' },
body: file,
})
Pridėjus content-type prie signableHeaders, URL susiejamas su tuo tipu, todėl įkėlimas su kitu Content-Type atmetamas. Boto3 atitikmuo yra generate_presigned_url('put_object', Params={'Bucket': ..., 'Key': ..., 'ContentType': 'application/pdf'}), o klientas turi siųsti tą pačią antraštę.
Trys dalykai, kuriuos reikia patikrinti prieš įkeliant iš naršyklės:
- CORS. Bucket reikia CORS taisyklės, leidžiančios jūsų kilmę ir
PUTmetodą. Multipart įkėlimams ji taip pat turi atskleistiETagantraštę, nes naršyklė turi ją perskaityti iš kiekvienos dalies. - Fiksuotas raktas. Unikalų raktą generuokite serveryje (pavyzdžiui, su UUID prefiksu), kad lankytojas negalėtų perrašyti kito žmogaus failo.
- Kontrolinės sumos. Dabartiniai AWS SDK pagal numatytuosius nustatymus prie įkėlimų prideda CRC kontrolinę sumą. Jei presigned įkėlimai į S3 suderinamą teikėją nepavyksta dėl parašo ar kontrolinės sumos klaidų, klientui nustatykite
requestChecksumCalculation: 'WHEN_REQUIRED'.
Presigned POST yra atskiras mechanizmas paprastoms HTML formoms, su politika, kuri gali riboti dydį ir turinio tipą. Ne kiekvienas S3 suderinamas teikėjas jį palaiko (R2 nepalaiko), todėl presigned PUT yra universalesnis pasirinkimas.
Dideli failai: presigned multipart įkėlimai
Pavienis PUT į S3 ribojamas 5 GB, o AWS siūlo multipart nuo maždaug 100 MB. Multipart padalija failą į iki 10 000 dalių, kiekviena nuo 5 MiB iki 5 GiB, išskyrus paskutinę, kurios įkeliamos nepriklausomai, lygiagrečiai ir su pakartojimais kiekvienai daliai. Pasirašymas veikia kiekvienai daliai: serveris pradeda įkėlimą, kiekvienai daliai pasirašo po vieną UploadPart URL, naršyklė siunčia kiekvieną gabalą ir grąžina jo ETag, o serveris užbaigia įkėlimą.
import {
CreateMultipartUploadCommand,
UploadPartCommand,
CompleteMultipartUploadCommand,
} from '@aws-sdk/client-s3'
const { UploadId } = await client.send(
new CreateMultipartUploadCommand({ Bucket: 'my-bucket', Key: 'video/raw.mov' })
)
const partUrl = await getSignedUrl(
client,
new UploadPartCommand({ Bucket: 'my-bucket', Key: 'video/raw.mov', UploadId, PartNumber: 1 }),
{ expiresIn: 3600 }
)
await client.send(
new CompleteMultipartUploadCommand({
Bucket: 'my-bucket',
Key: 'video/raw.mov',
UploadId,
MultipartUpload: { Parts: [{ PartNumber: 1, ETag: etagFromPartResponse }] },
})
)
Pridėkite gyvavimo ciklo taisyklę, kuri po kelių dienų nutraukia nebaigtus multipart įkėlimus, kitaip apleistos dalys toliau užims apmokestinamą vietą.
Presigned URL R2, B2, Spaces ir Wasabi
Teikėjai, įgyvendinantys S3 API su SigV4, priima tą patį kodą: pakeičiate tik endpoint, regioną ir raktus. Detalės skiriasi, todėl pasitikrinkite teikėjo dokumentaciją:
- Cloudflare R2 palaiko presigned
GET,HEAD,PUTirDELETE, su galiojimu nuo 1 sekundės iki 7 dienų. Jis nepalaiko presignedPOST, o presigned URL veikia tik S3 API domene (<ACCOUNT_ID>.r2.cloudflarestorage.com), ne pasirinktiniuose domenuose. Naudokiteregion: 'auto'. - Backblaze B2 nurodo, kad jo S3 suderinama API palaiko presigned URL, sugeneruotus su AWS CLI ar SDK.
- DigitalOcean Spaces ir Wasabi veikia su tais pačiais SDK kvietimais, nukreiptais į jų endpoint.
Kiekvieno teikėjo kainas rasite S3, R2, Spaces, Wasabi ir B2 palyginime.
Dažnos presigned URL klaidos ir kaip jas ištaisyti
| Klaida | Įprasta priežastis | Sprendimas |
|---|---|---|
SignatureDoesNotMatch | Metodas, antraštės ar užklausa skiriasi nuo pasirašytųjų; nesinchronizuotas laikrodis | Siųskite tą patį Content-Type ir antraštes; sinchronizuokite laikrodį su NTP |
AccessDenied „Request has expired“ | URL galiojimas pasibaigė po X-Amz-Date + X-Amz-Expires | Sugeneruokite naują URL; sutrumpinkite laiką tarp pasirašymo ir naudojimo |
| URL nustoja galioti anksčiau nei prašyta | Pasirašyta laikinais duomenimis (vaidmuo, EC2, ECS, Lambda) | Pasirašykite duomenimis, kurie galioja tiek, kiek turi galioti nuoroda |
ExpiredToken | Baigėsi STS sesija už X-Amz-Security-Token | Atnaujinkite prisijungimo duomenis prieš pasirašydami |
403 AccessDenied naujam URL | Pasirašiusysis neturi s3:GetObject ar s3:PutObject arba tai draudžia politika | Suteikite teisę pasirašančiam subjektui; patikrinkite bucket politikas |
AuthorizationQueryParametersError | Galiojimas virš 604 800 sekundžių arba netinkama duomenų apimtis | Laikykite X-Amz-Expires ne daugiau 7 dienų; pasirašykite bucket regione |
| Naršyklę blokuoja CORS | Bucket neturi CORS taisyklės jūsų kilmei ir metodui | Pridėkite CORS taisyklę su savo kilme, GET/PUT ir atskleistu ETag |
AccessDenied su HeadersNotSigned | Range pasirašyta, bet If-Range išsiųsta nepasirašyta | Pridėkite If-Range prie pasirašytų antraščių |
Įmonių tarpiniai serveriai, perrašantys antraštes ar užklausos eilutes, taip pat sugadina parašus. Jei URL veikia iš vieno tinklo, bet ne iš kito, išbandykite be tarpinio serverio.
Saugumo gerosios praktikos
AWS presigned URL vadina bearer tokens ir rekomenduoja juos saugoti. Praktiškai:
- Laikykite juos trumpus. Minutės įkėlimams ir jautriems failams, valandos įprastiems atsisiuntimams. Kai kam nors vėl reikia failo, sugeneruokite naują.
- Pasirašykite siaura tapatybe. Specialus IAM vartotojas ar vaidmuo, kuris gali tik skaityti (ar tik rašyti) atitinkamą prefiksą, apriboja žalą, jei nuoroda nutekės.
- Pridėkite apsaugas bucket politikoje. Sąlyga
s3:signatureAgeatmeta parašus, senesnius nei nustatytas amžius, oaws:SourceIpriboja, kurie tinklai gali juos naudoti. - Neregistruokite jų žurnaluose. Pilni presigned URL programų žurnaluose, analitikoje ar pokalbių istorijoje yra veikiantys prisijungimo duomenys, kol nenustos galioti.
- Įvertinkite, ko jiems trūksta. Nėra slaptažodžio, atsisiuntimų skaičiaus ir atskiros nuorodos atšaukimo, todėl, kai to reikia, priekyje pastatykite programą.
Išsamiau apie bendrinimą, su variantais, kurie prideda šias kontrolės priemones, skaitykite straipsnyje kaip bendrinti S3 failus nepadarant bucket viešo.
Kaip Nubbo naudoja presigned URL
Nubbo sukurta šiuo principu. Kai įkeliate naršyklėje, serveris pasirašo PUT (arba, nuo 100 MB, multipart įkėlimą su trimis lygiagrečiomis dalimis), o jūsų naršyklė siunčia baitus tiesiai į jūsų bucket. Pavienių failų atsisiuntimai naudoja presigned GET URL, galiojančius vieną valandą. Jūsų prieigos raktai saugomi užšifruoti AES-256-GCM ir naudojami tik serveryje pasirašymui.
Bendrinimo nuorodos prideda tai, ko trūksta paprastiems presigned URL: pasirinktinį slaptažodį, galiojimo datą ir atsisiuntimų limitą, kuriuos Nubbo patikrina prieš išduodama trumpalaikį URL, o nuorodą galite bet kada išjungti. Kelių failų ZIP atsisiuntimai sudaromi jūsų naršyklėje, kuri kiekvieną failą atsisiunčia tiesiai iš jūsų bucket: Nubbo niekada nemato turinio. Viena sąžininga išimtis: miniatiūros įrašomos į jūsų pačių bucket aplanke .nubbo-thumbs/. Tai veikia vienodai su Amazon S3, Cloudflare R2, DigitalOcean Spaces, Wasabi, Backblaze B2 ir viešais S3 suderinamais endpoint.
Dažnai užduodami klausimai
Kas yra presigned URL S3?
Tai įprasta HTTPS nuoroda į vieną objektą privačiame bucket su parašu, pridėtu prie užklausos eilutės. Kas turi nuorodą, gali atlikti vienintelę operaciją, kuriai ji pasirašyta, dažniausiai atsisiuntimą (GET) ar įkėlimą (PUT), kol ji nustos galioti. Bucket lieka privatus, o nuorodą naudojančiam žmogui nereikia AWS prisijungimo duomenų.
Koks didžiausias S3 presigned URL galiojimo laikas?
Septynios dienos (604 800 sekundžių), kai pasirašote su Signature Version 4 ir ilgalaikiais IAM vartotojo raktais. URL, pasirašytas laikinais prisijungimo duomenimis, pavyzdžiui, prisiimtu vaidmeniu ar EC2 instance profile, nustoja veikti, kai baigiasi tų duomenų galiojimas, net jei prašėte ilgiau. S3 konsolėje galite rinktis nuo 1 minutės iki 12 valandų.
Ką reiškia X-Amz-Algorithm, X-Amz-Credential, X-Amz-Date, X-Amz-Expires, X-Amz-SignedHeaders ir X-Amz-Signature?
Tai SigV4 autentifikavimo parametrai. Algorithm yra pasirašymo metodas (AWS4-HMAC-SHA256), Credential yra jūsų prieigos rakto ID plius datos, regiono ir paslaugos apimtis, Date yra laikas, kada URL pasirašytas, Expires yra kiek sekundžių jis galioja, SignedHeaders išvardija parašo apimamas antraštes, o Signature yra pats parašas. X-Amz-Security-Token atsiranda tik tada, kai URL pasirašytas laikinais prisijungimo duomenimis.
Ar galiu atšaukti S3 presigned URL, kol jis dar galioja?
Ne po vieną. Presigned URL anksčiau nustoja veikti tik tada, kai jį pasirašę prisijungimo duomenys atšaukiami, ištrinami ar išjungiami arba kai bucket politika draudžia užklausą. Jei reikia atšaukti atskiras nuorodas, priekyje pastatykite programą, kuri trumpalaikius URL išduoda tik po savo patikrų.
Ar S3 presigned URL saugūs?
Parašo negalima suklastoti ar pakeisti, o bucket lieka privatus. Tačiau AWS presigned URL apibūdina kaip bearer tokens: kiekvienas, gavęs nuorodą, gali ją naudoti kiek tik nori kartų, kol ji nustos galioti. Galiojimo laiką laikykite trumpą, naudokite HTTPS ir nepublikuokite nuorodų ten, kur jas galima nukopijuoti.
Ar presigned URL veikia su Cloudflare R2, Backblaze B2 ar Wasabi?
Teikėjai, įgyvendinantys S3 API su Signature Version 4, paprastai juos palaiko, ir naudojate tuos pačius SDK kvietimus su teikėjo endpoint. Pavyzdžiui, Cloudflare R2 palaiko presigned GET, HEAD, PUT ir DELETE su galiojimu nuo 1 sekundės iki 7 dienų, bet nepalaiko POST formų įkėlimų ir pasirinktinių domenų.
Kodėl mano presigned URL grąžina SignatureDoesNotMatch?
AWS nurodo tris dažnas priežastis: nesinchronizuotas kompiuterio laikrodis, tarpinis serveris, keičiantis antraštes ar užklausos eilutę, ir užklausa, kurios metodas, antraštės ar parametrai skiriasi nuo pasirašytųjų. Įkėlimų atveju dažniausia kaltininkė yra kitokia Content-Type antraštė nei ta, kuri naudota generuojant URL.
Šaltiniai
Kainos ir ribos paimtos iš toliau nurodytų oficialių puslapių. Teikėjai jas keičia, todėl patikrinkite prieš apsispręsdami.
- Amazon S3: objektų atsisiuntimas ir įkėlimas su presigned URL
- AWS IAM: autentifikavimo metodai (SigV4 užklausos parametrai)
- Amazon S3 API: užklausų autentifikavimas užklausos parametrais (SigV4)
- AWS CLI žinynas: s3 presign
- Boto3 žinynas: generate_presigned_url
- AWS SDK for JavaScript v3: @aws-sdk/s3-request-presigner
- Amazon S3: multipart įkėlimo ribos
- AWS SDKs and Tools: Amazon S3 duomenų vientisumo apsauga
- Cloudflare R2: presigned URL
- Backblaze: ar B2 S3 Compatible API palaiko presigned URL?