Πρώτο μάθημα: Μην διαρρέετε τα μυστικά σας σε μεσαία εικόνα μετά

Ο καλύτερος τρόπος για να αποθηκεύσετε μυστικά στην εφαρμογή σας δεν είναι να αποθηκεύετε μυστικά στην εφαρμογή σας

Αποποίηση: Η μέθοδος που περιγράφεται σε αυτό το άρθρο βασίζεται σε μεγάλο βαθμό στο AWS. Τούτου λεχθέντος, η έννοια μπορεί να ισχύει και για άλλους παρόχους ...

Αν έχετε κατασκευάσει ποτέ μια εφαρμογή στο Διαδίκτυο, συναντήσατε τον αγώνα διατήρησης μυστικών (διαπιστευτήρια βάσης δεδομένων, κλειδιά api, κ.λπ.) στο διακομιστή σας.

Ιστορικά, οι προγραμματιστές βρήκαν διάφορους τρόπους για να το επιτύχουν αυτό. Κάθε μία από αυτές φέρει ένα ορισμένο επίπεδο ασφάλειας και ευκολίας. Θα σας καθοδηγήσω για να μπορέσετε να πάρετε μια αίσθηση από πού έρχομαι.

Αποθήκευση μυστικών στον κώδικα σας

# settings / instance_settings.py
STRIPE_API_KEY = '3ef8-843a-49dc-a34d' # Μην πείτε σε κανέναν! plz;

Αυτή είναι προφανώς η πιο βολική μέθοδος. Γράφετε το κλειδί API στον κώδικα σας ως σταθερό, στη συνέχεια τον σπρώχνετε στον έλεγχο της πηγής σας, και το voilà!

Αλλά, είναι και η λιγότερο ασφαλής μέθοδος. Μόλις επέτρεψε να διανεμηθεί ένα σημαντικό μυστικό στον υπολογιστή του κάθε προγραμματιστή (ή στις εξωτερικές μονάδες δίσκου), στον αποθηκευτικό χώρο του παροχέα ελέγχου πηγής, στον εξυπηρετητή του παροχέα CI σας κλπ. Αυτό αυξάνει τον κίνδυνο να διαρρεύσει αυτό το μυστικό.

Αποθήκευση μυστικών στο περιβάλλον

stripe_api_key = os.environ ["STRIPE_API_KEY"]

Αυτό είναι ένα που έχω χρησιμοποιήσει αρκετά συχνά. Θα χρειαστεί είτε να ορίσετε χειροκίνητα τις μεταβλητές περιβάλλοντος σε κάθε διακομιστή είτε να χρησιμοποιήσετε κάποιο είδος ενορχηστρωτή για να το χειριστείτε αυτό για σας, το οποίο είναι ελαφρώς λιγότερο βολικό από την προηγούμενη μέθοδο. Παρ 'όλα αυτά, έχει το πλεονέκτημα ότι μόνο ορισμένα εμπιστευμένα άτομα έχουν πρόσβαση σε αυτό.

Υπάρχουν ακόμα ορισμένα προβλήματα: μια απλή λανθασμένη διαμόρφωση (όπως η εκτέλεση ενός διακομιστή παραγωγής στη λειτουργία εντοπισμού σφαλμάτων) ή ένα σφάλμα ασφαλείας μπορεί να οδηγήσει στη διαρροή όλων των μεταβλητών περιβάλλοντος.

Αποθήκευση μυστικών στη βάση δεδομένων

Θα αναφερθώ σύντομα σε αυτό το θέμα: θα χρειαστεί ακόμα να έχετε τα διαπιστευτήρια της βάσης δεδομένων σας έξω από κάπου, επομένως να νικήσετε τον σκοπό της τοποθέτησης των μυστικών σας εκεί. Επιπλέον, η καθημερινή δημιουργία αντιγράφων ασφαλείας όλων των κλειδιών API των υπηρεσιών σας αυξάνει επίσης τον κίνδυνο μιας διαρροής σε κάποιο σημείο.

Χρησιμοποιώντας μια υπηρεσία συγχρονισμού μυστικών

Υπάρχουν SaaS που προσφέρουν να φροντίζουν τα κλειδιά API και άλλα μυστικά για εσάς. Θα τους κρατήσει ασφαλείς και θα σας επιτρέψουν να τους ζητήσετε από την υπηρεσία τους, όπως απαιτείται. Εξακολουθούμε να αντιμετωπίζουμε το ίδιο πρόβλημα με την προηγούμενη μέθοδο: θα χρειαστείτε ένα πολύ μυστικό κλειδί API για να λάβετε όλα τα κλειδιά API.

Αποθήκευση μυστικών στον κωδικό σας ... αλλά κρυπτογραφημένο

Μια σύγχρονη έκδοση της πρώτης μεθόδου είναι να κρυπτογραφήσετε τα μυστικά στον κώδικα σας, μη εκθέτοντας έτσι τις αξίες τους στον έλεγχο πηγής, σε άλλους προγραμματιστές κ.ο.κ. Ωστόσο, για να αποκρυπτογραφήσει αυτά τα μυστικά, ο διακομιστής πρέπει να διαχειριστεί ένα κλειδί. Αυτό έρχεται πίσω στο θέμα της διανομής και διατήρησης ενός μεγάλου μυστικού που ξεκλειδώνει όλα τα άλλα μυστικά.

Γιατί δεν είναι ασφαλές;

Όλες αυτές οι μέθοδοι έχουν το ίδιο χαρακτηριστικό. εξακολουθούν να περιλαμβάνουν τη δημιουργία μυστικών στον διακομιστή σας και αυτά θα μπορούσαν να διαρρεύσουν ή να κλαπούν

Στη χειρότερη περίπτωση

Φανταστείτε το ακόλουθο σενάριο. Ένας εισβολέας έσπασε στο διακομιστή σας χρησιμοποιώντας ένα θέμα ευπάθειας στο Apache. Στη συνέχεια ξεκινά την αναζήτηση διαπιστευτηρίων βάσης δεδομένων και κλειδιών API στο αρχείο ρυθμίσεων, στον κώδικα, στο περιβάλλον. Αν τα μυστικά σας είναι κάπως κρυμμένα / κρυπτογραφημένα, ο επιτιθέμενος δεν θα βρει τίποτα. Αλλά αυτό δεν σημαίνει ότι θα σταματήσει εκεί. Χρησιμοποιώντας κάτι σαν το LiME, ο χάκερ θα μπορούσε ακόμα να περιηγηθεί στη χωρητικότητα μνήμης του διακομιστή για να εξαγάγει αυτά τα μυστικά.

Μπορούμε να κάνουμε καλύτερα

Παρουσιάζοντας:

Πρόσβαση σε υπηρεσία χωρίς διαπιστευτήρια χρησιμοποιώντας μια ταυτότητα API Gateway ως διακομιστή μεσολάβησης

(Είμαι τρομερός στο να βρίσκω ελκυστικά ονόματα και αυτό δεν είναι πραγματικά εμπορικό σήμα)

ΣΦΑΙΡΙΚΗ ΕΙΚΟΝΑ

Με λίγα λόγια, χρησιμοποιούμε τον ρόλο του στιγμιότυπου της παράτασής μας EC2 για να κάνουμε μια ασφαλή κλήση σε μια πύλη API, η οποία στη συνέχεια πληρεξούται στην επιθυμητή υπηρεσία, αφού τροποποιήσει το αίτημα προσθέτοντας τα απαιτούμενα διαπιστευτήρια. Ew! Αυτές είναι πολλές πληροφορίες για μια μόνο πρόταση.

Λένε ότι μια φωτογραφία αξίζει 1000 λέξεις. ΠΡΟΣΚΟΠΗΣΗ ΠΡΟΚΛΗΣΗΣ

Ακόμη χάσατε; Ας αναλύσουμε αυτό

Πρώτον, για να λειτουργήσει αυτό, πρέπει να χρησιμοποιήσουμε τον εγχώριο τρόπο για τις περιπτώσεις EC2 (ή ECS Containers και Lambdas) για να πραγματοποιήσετε κλήσεις σε άλλους πόρους AWS, χρησιμοποιώντας τους ρόλους του IAM.

Δεύτερον, πρέπει να δημιουργήσουμε έναν πόρο Rest API στο API Gateway. Υπάρχουν ορισμένες συγκεκριμένες διαμορφώσεις που πρέπει να εφαρμοστούν, ώστε να μπορούν να περάσουν το σώμα, οι κεφαλίδες και οι παράμετροι ερωτήματος. Επιπλέον, πρέπει να αλλάξουμε το αίτημα, ώστε να μπορέσουμε να εισάγουμε τα διαπιστευτήρια της υπηρεσίας στόχευσης. Τέλος, πρέπει να ενεργοποιήσουμε το μυστικό όπλο: έγκριση βάσει IAM.

Το τρίτο και το τελευταίο βήμα συνίστανται στην υπογραφή της διεύθυνσης URL πριν την κλήση στις επιθυμητές υπηρεσίες proxy.

¿Que?

Για όσους από εσάς δεν είστε πολύ εξοικειωμένοι με τις τεχνολογίες που μόλις ανέφερα και εξακολουθείτε να μην είστε σίγουροι για το τι είναι αυτό, εδώ είναι μια σύγκριση πριν και μετά τη χρήση της υπηρεσίας πρόσβασης χωρίς πιστοποιήσεις, χρησιμοποιώντας ως πύλη API Gateway API με πιστοποίηση IAM:

Θα χρησιμοποιήσω το γνωστό GitHub API και τον Postman για αυτή την επίδειξη:

Πριν από την (απευθείας κλήση στο GitHub):

Μετά την κλήση μέσω πληκτρολογίου API:

Μπορώ ήδη να ακούσω να λέτε:

Μας είπατε ότι αυτό ήταν πιστοποίηση-λιγότερο και βλέπω ένα κλειδί πρόσβασης, ένα μυστικό κλειδί και ένα συμβολικό!

Αυτό συμβαίνει επειδή ο φορητός υπολογιστής μου δεν έχει το μυστικό όπλο. Μόλις το ξεκινήσετε και εκτελείτε σε μια παρουσία EC2, αυτά τα προσωρινά διαπιστευτήρια ασφαλείας θα ανακτηθούν αυτόματα από τα μεταδεδομένα των στιγμιότυπων. Εάν η έννοια των προσωρινών διαπιστευτηρίων είναι νέα για εσάς, εδώ είναι ένα απόσπασμα από την τεκμηρίωση (έμφαση δική μου):

Σε μια εφαρμογή στην περίπτωση [...] παρέχονται τα δικαιώματα για τις ενέργειες και τους πόρους που έχετε ορίσει για το ρόλο μέσω των διαπιστευτηρίων ασφαλείας που σχετίζονται με το ρόλο. Αυτά τα διαπιστευτήρια ασφαλείας είναι προσωρινά και τα περιστρέφουμε αυτόματα. Κάνουμε νέα διαπιστευτήρια διαθέσιμα τουλάχιστον πέντε λεπτά πριν από τη λήξη των παλαιών διαπιστευτηρίων.

Έτσι, για να είμαστε δίκαιοι, μια ακριβέστερη περιγραφή αυτής της μεθόδου θα ήταν η πρόσβαση στην υπηρεσία χρησιμοποιώντας μια IAM authenticated API Gateway ως διακομιστή μεσολάβησης χωρίς τη χρήση μακροπρόθεσμων διαπιστευτηρίων. Ωστόσο, μπορούμε να συμφωνήσουμε ότι τα "βραχυπρόθεσμα προσωρινά διαπιστευτήρια που χρησιμοποιούνται για την υπογραφή κλήσεων σε υπηρεσίες proxied που περιορίζονται μέσω IAM" είναι λιγότερο ελκυστικά για τους επιτιθέμενους από τα κανονικά κλειδιά API και άλλα μακροπρόθεσμα μυστικά.

Πρόκειται για μια τεράστια αναβάθμιση από την άποψη της ασφάλειας

Σημαντικές βελτιώσεις ασφαλείας:

  • Τα προσωρινά διαπιστευτήρια δεν πρέπει να αντιμετωπίζονται ποτέ από προγραμματιστές
  • Είναι ερωτηματολογούνται προγραμματιστικά, ώστε να μην χρειάζεται να γράφονται σε ένα αρχείο ρυθμίσεων
  • Αν διαρρεύσει ή κλαπεί, αυτά τα προσωρινά διαπιστευτήρια θα λειτουργούν το πολύ μία ώρα
  • Όλα τα αιτήματα μπορούν να συνδεθούν στο CloudWatch για έλεγχο
  • Μπορείτε να περιορίσετε το στοχευμένο API χρησιμοποιώντας μια πολιτική IAM

Το τελευταίο σημείο σφαίρας είναι ιδιαίτερα χρήσιμο όταν εργάζεστε με ένα API όπως το GitHub που δεν διαθέτει μοντέλο αδειών με λεπτόκοκκο τρόπο. Χρησιμοποιώντας την ακόλουθη πολιτική IAM, μπορώ να περιορίσω το API μου να επιτρέπει μόνο τη μέθοδο GET στο τελικό σημείο / repos / PokaInc / test-github-api / issues.

{
    "Έκδοση": "2012-10-17",
    "Δήλωση": [
        {
            "Δράση": [
                "execute-api: Invoke"
            ],
            "Πόρος": [
                "arn: aws: execute-api: us-east-1: 123456789010: w974f1rs6e / dev / GET / repos / PokaIn / test-github-api /
            ],
            "Effect": "Allow"
        }}
    ]
}}

Αλλά περιμένετε, υπάρχουν περισσότερα!

Άλλα οφέλη από τη χρήση του Gateway API ως διακομιστή μεσολάβησης

  • Στατιστικά χρήσης. Αυτό μπορεί να είναι χρήσιμο για τον εντοπισμό τάσεων και την αποτροπή περιορισμού των επιτοκίων από υπηρεσίες τρίτων.
  • Ξύλευση. Όταν είναι ενεργοποιημένη, μπορείτε να έχετε λεπτομερή αρχεία καταγραφής κάθε αιτήματος, συμπεριλαμβανομένης της προέλευσης και των παραμέτρων που χρησιμοποιούνται.
  • Caching. Έχετε προβλήματα λανθάνοντος χρόνου ή περιορισμού του επιτοκίου; Με τρεις γραμμές του κώδικα CloudFormation μπορείτε να προσθέσετε ένα back-up κρυφής μνήμης στον πληρεξούσιό σας.
  • Τοπική ανάπτυξη. Οι προγραμματιστές που χρησιμοποιούν τοπικά έναν χρήστη IAM μπορούν να έχουν άμεση πρόσβαση στις υπηρεσίες proxied αντί να βασίζονται σε πιστοποιήσεις που έχουν κωδικοποιηθεί με σκληρό δίσκο στον υπολογιστή τους.

Σε αυτό το σημείο θα υποθέσω ότι έχετε πουλήσει στην ιδέα και θέλετε να δοκιμάσετε τη μέθοδο για τον εαυτό σας.

Ο κώδικας

Λαμβάνοντας υπόψη εδώ στο Poka είμαστε CloudFormation afi · cio · nados, έχω δημιουργήσει ένα πρότυπο proof-concept που είναι διαθέσιμο στο GitHub.

Τροφοδοσία

Για να δημιουργήσετε τον διακομιστή μεσολάβησης, ακολουθήστε τις οδηγίες στο README.md.

Χρήση του διακομιστή μεσολάβησης

Αυτό περιγράφεται επίσης στο readme, αλλά θα το ενσωματώσω εδώ, για να μπορώ να σας πείσω ότι δεν είναι μαύρη μαγεία.

Ας εξετάσουμε αυτό το μπλοκ κώδικα:

επιστροφή AWSRequestsAuth (
      [...]
      ** boto_utils.get_credentials ()
)

Σε αυτό το σημείο θα είχαμε συνήθως δει αναγνωρισμένα πιστοποιητικά, πρόσβαση σε αρχείο ρυθμίσεων ή ερώτημα στο περιβάλλον. Αντίθετα, αυτή η μέθοδος ζητά την υπηρεσία μεταδεδομένων για προσωρινά κλειδιά. Εάν ο ρόλος στιγμιότυπου EC2 έχει επαρκείς άδειες, η κλήση θα μεταβεί στο GitHub, διαφορετικά, η πύλη API θα την απορρίψει.

συμπέρασμα

Ελπίζω ότι αυτή η ανάρτηση βοήθησε στην ευαισθητοποίηση για τα κακώς προστατευμένα μυστικά στους διακομιστές εφαρμογών και πως η χρήση του API Gateway ως πληρεξούσιος μπορεί να σας ωφελήσει πέρα ​​από την πρόσθετη ασφάλεια.

Προειδοποιήσεις (και ο τρόπος αντιμετώπισης τους)

  • Τι γίνεται αν θέλω να πληρώσω μια εσωτερική υπηρεσία που δεν εκτίθεται στο Διαδίκτυο;

Η εξήγηση θα μπορούσε να έχει τη δική του αφιερωμένη θέση blog. Αλλά η σύντομη ιστορία σύντομη, μπορείτε να παρέχετε ένα VPC Enabled AWS Lambda ως στόχο του πληρεξούσιου API Gateway. Η Lambda θα πρέπει να περάσει τις κεφαλίδες, τις παραμέτρους του ερωτήματος και το σώμα στην εσωτερική υπηρεσία, να συγκεντρώσει την απάντηση και να την επιστρέψει στην πύλη API.

  • Αυτό λειτουργεί καλά με API REST, αλλά τι γίνεται με τις υπηρεσίες TCP, όπως μια σχεσιακή βάση δεδομένων ή έναν διακομιστή cache;

Και πάλι, αυτό θα αξίζει μια πλήρη θέση blog. Με λίγα λόγια, μπορούμε να δημιουργήσουμε μια μικρο-υπηρεσία (προσπελάσιμη, υποθέσατε, μια IAM authenticated API Gateway) που θα δημιουργήσει πιστοποιήσεις επί τόπου για τις επιθυμητές υπηρεσίες. Για παράδειγμα, εάν ζητηθεί από τις μικροεπιχειρήσεις τα διαπιστευτήρια του PostgreSQL, μπορεί να εκδώσει μια εντολή CREATE ROLE με έναν κωδικό που δημιουργήθηκε τυχαία. Επιπλέον, ο ρόλος θα μπορούσε να έχει χρόνο για να ζήσει χρησιμοποιώντας την ιδιότητα VALID UNTIL.

Εναλλακτικές λύσεις

Δεν εκτελείτε το φόρτο εργασίας σας στο AWS; Αυτή η μέθοδος δεν μπορεί να λειτουργήσει για εσάς; Υπάρχουν και άλλα εργαλεία που μπορούν να σας βοηθήσουν να αντιμετωπίσετε τη διαχείριση μυστικών.

  • http://engineering.nike.com/cerberus/
  • https://www.vaultproject.io/
  • https://docs.docker.com/engine/swarm/secrets/

Αναφορές για αυτό το άρθρο:

http://blog.arkency.com/2017/07/how-to-safely-store-api-keys-in-rails-apps/
https://blog.rackspace.com/securing-application-secrets-with-ec2-parameter-store
https://www.envkey.com/
https://www.hashicorp.com/blog/Vault-announcement/
https://docs.docker.com/engine/swarm/secrets/
http://docs.aws.amazon.com/apigateway/latest/developerguide/permissions.html
http://docs.aws.amazon.com/IAM/latest/UserGuide/id_roles_use_switch-role-ec2.html
http://docs.aws.amazon.com/general/latest/gr/signature-v4-examples.html

Ευχαριστώ ιδιαιτέρως τους Tea Rudolf, Etienne Talbot, Simon-Pierre Gingras, Maxime Leblanc και Marilou Simard-Baril για τις διορθώσεις (Ναι, χρειάζομαι πολλούς ανθρώπους για να αναθεωρήσω τα αγγλικά μου) και χάρη στην Julie Dorion-Bélanger για τις εικονογραφήσεις.

Έχετε ερωτήσεις / προτάσεις σχετικά με αυτήν την ανάρτηση; Γράψτε ένα σχόλιο παρακάτω και θα κάνω το παν για να απαντήσω.