Differenziellen Datenschutz erweitern

In diesem Dokument wird anhand von Beispielen gezeigt, wie Sie Differential Privacy für den differenziellen Datenschutz in BigQuery erweitern.

Überblick

Mit BigQuery können Sie differenziellen Datenschutz (Differential Privacy) auf Multi-Cloud-Datenquellen und externe Differential-Privacy-Bibliotheken erweitern. Dieses Dokument enthält Beispiele für die Anwendung von differentiellem Datenschutz für Multi-Cloud-Datenquellen wie AWS S3 mit BigQuery Omni, für den Aufruf einer externen Differential-Privacy-Bibliothek über eine Remote-Funktion und für die Durchführung von Differential-Privacy-Aggregationen mit PipelineDP, einer Python-Bibliothek, die mit Apache Spark und Apache Beam ausgeführt werden kann.

Weitere Informationen zum differenziellen Datenschutz finden Sie unter Differential Privacy verwenden.

Differential Privacy mit BigQuery Omni

Der differenzielle Datenschutz in BigQuery unterstützt Aufrufe von Multi-Cloud-Datenquellen wie AWS S3. Im folgenden Beispiel wird die externe Datenquelle foo.wikidata abgefragt und es wird differenzieller Datenschutz angewendet. Weitere Informationen zur Syntax der differenziellen Datenschutzklausel finden Sie im Abschnitt zur Differenziellen Datenschutzklausel.

SELECT
  WITH
    DIFFERENTIAL_PRIVACY
      OPTIONS (
        epsilon = 1,
        delta = 1e-5,
        privacy_unit_column = foo.wikidata.es_description)
      COUNT(*) AS results
FROM foo.wikidata;

Dieses Beispiel gibt in etwa folgende Ergebnisse zurück:

-- These results will change each time you run the query.
+----------+
| results  |
+----------+
| 3465     |
+----------+

Weitere Informationen zu den Einschränkungen von BigQuery Omni finden Sie unter Einschränkungen.

Externe differenzielle Datenschutzbibliotheken mit Remote-Funktionen aufrufen

Sie können externe Differential-Privacy-Bibliotheken mit Remote-Funktionen aufrufen. Über den folgenden Link wird eine Remote-Funktion verwendet, um eine externe, von Tumult Analytics gehostete Bibliothek aufzurufen, um null-konzentrierten differenziellen Datenschutz für ein Verkaufs-Dataset im Einzelhandel zu nutzen.

Informationen zur Arbeit mit Tumult Analytics finden Sie im Tumult Analytics-Einführungsbeitrag.

Differential-Privacy-Aggregationen mit PipelineDP

PipelineDP ist eine Python-Bibliothek, die differenzielle Datenschutzaggregationen durchführt und mit Apache Spark und Apache Beam ausgeführt werden kann. BigQuery kann gespeicherte Apache Spark-Prozeduren ausführen, die in Python geschrieben wurden. Weitere Informationen zum Ausführen gespeicherter Prozeduren von Apache Spark finden Sie unter Mit gespeicherten Prozeduren für Apache Spark arbeiten.

Im folgenden Beispiel wird eine Differential-Privacy-Aggregation mithilfe der PipelineDP-Bibliothek durchgeführt. Sie verwendet das öffentliche Dataset von Chicago Taxi Trips und berechnet für jedes Taxi die Anzahl der Fahrten sowie die Summe und den Mittelwert der Trinkgelder für diese Fahrten.

Hinweise

Ein Apache Spark-Standard-Image enthält PipelineDP nicht. Sie müssen ein Docker-Image erstellen, das alle erforderlichen Abhängigkeiten enthält, bevor Sie eine gespeicherte PipelineDP-Prozedur ausführen. In diesem Abschnitt wird beschrieben, wie Sie ein Docker-Image erstellen und an Google Cloud übertragen.

Bevor Sie beginnen, müssen Sie Docker auf Ihrem lokalen Computer installiert haben und die Authentifizierung zum Übertragen von Docker-Images an gcr.io einrichten. Weitere Informationen zum Übertragen von Docker-Images finden Sie unter Images hoch- und herunterladen.

Docker-Image erstellen und übertragen

So erstellen und senden Sie ein Docker-Image per Push-Verfahren mit den erforderlichen Abhängigkeiten:

  1. Erstellen Sie einen lokalen Ordner DIR.
  2. Laden Sie das Miniconda-Installationsprogramm mit der Python 3.9-Version in DIR herunter.
  3. Speichern Sie den folgenden Text im Dockerfile.

    
      # Debian 11 is recommended.
      FROM debian:11-slim
    
      # Suppress interactive prompts
      ENV DEBIAN_FRONTEND=noninteractive
    
      # (Required) Install utilities required by Spark scripts.
      RUN apt update && apt install -y procps tini libjemalloc2
    
      # Enable jemalloc2 as default memory allocator
      ENV LD_PRELOAD=/usr/lib/x86_64-linux-gnu/libjemalloc.so.2
    
      # Install and configure Miniconda3.
      ENV CONDA_HOME=/opt/miniconda3
      ENV PYSPARK_PYTHON=${CONDA_HOME}/bin/python
      ENV PATH=${CONDA_HOME}/bin:${PATH}
      COPY Miniconda3-py39_23.1.0-1-Linux-x86_64.sh .
      RUN bash Miniconda3-py39_23.1.0-1-Linux-x86_64.sh -b -p /opt/miniconda3 \
      && ${CONDA_HOME}/bin/conda config --system --set always_yes True \
      && ${CONDA_HOME}/bin/conda config --system --set auto_update_conda False \
      && ${CONDA_HOME}/bin/conda config --system --prepend channels conda-forge \
      && ${CONDA_HOME}/bin/conda config --system --set channel_priority strict
    
      # The following packages are installed in the default image, it is
      # strongly recommended to include all of them.
      #
      # Use mamba to install packages quickly.
      RUN ${CONDA_HOME}/bin/conda install mamba -n base -c conda-forge \
      && ${CONDA_HOME}/bin/mamba install \
        conda \
        cython \
        fastavro \
        fastparquet \
        gcsfs \
        google-cloud-bigquery-storage \
        google-cloud-bigquery[pandas] \
        google-cloud-bigtable \
        google-cloud-container \
        google-cloud-datacatalog \
        google-cloud-dataproc \
        google-cloud-datastore \
        google-cloud-language \
        google-cloud-logging \
        google-cloud-monitoring \
        google-cloud-pubsub \
        google-cloud-redis \
        google-cloud-spanner \
        google-cloud-speech \
        google-cloud-storage \
        google-cloud-texttospeech \
        google-cloud-translate \
        google-cloud-vision \
        koalas \
        matplotlib \
        nltk \
        numba \
        numpy \
        openblas \
        orc \
        pandas \
        pyarrow \
        pysal \
        pytables \
        python \
        regex \
        requests \
        rtree \
        scikit-image \
        scikit-learn \
        scipy \
        seaborn \
        sqlalchemy \
        sympy \
        virtualenv
    
      RUN apt install -y python3-pip
      RUN pip install --no-input pipeline-dp==0.2.0
    
      # (Required) Create the 'spark' group/user.
      # The GID and UID must be 1099. Home directory is required.
      RUN groupadd -g 1099 spark
      RUN useradd -u 1099 -g 1099 -d /home/spark -m spark
      USER spark
    
    
  4. Führen Sie den folgenden Befehl aus:

    
    IMAGE=gcr.io/PROJECT_ID/DOCKER_IMAGE:0.0.1
    # Build and push the image.
    docker build -t "${IMAGE}"
    docker push "${IMAGE}"
    
    

    Ersetzen Sie Folgendes:

    • PROJECT_ID: das Projekt, in dem Sie das Docker-Image erstellen möchten.
    • DOCKER_IMAGE: der Name des Docker-Images.

    Das Image wird hochgeladen.

Gespeicherte PipelineDP-Prozedur ausführen

  1. Verwenden Sie zum Erstellen einer gespeicherten Prozedur die Anweisung CREATE PROCEDURE.

    CREATE OR REPLACE
    PROCEDURE
      `PROJECT_ID.DATASET_ID.pipeline_dp_example_spark_proc`()
      WITH CONNECTION `PROJECT_ID.REGION.CONNECTION_ID`
    OPTIONS (
      engine = "SPARK",
      container_image= "gcr.io/PROJECT_ID/DOCKER_IMAGE")
    LANGUAGE PYTHON AS R"""
    from pyspark.sql import SparkSession
    import pipeline_dp
    
    def compute_dp_metrics(data, spark_context):
    budget_accountant = pipeline_dp.NaiveBudgetAccountant(total_epsilon=10,
                                                          total_delta=1e-6)
    backend = pipeline_dp.SparkRDDBackend(spark_context)
    
    # Create a DPEngine instance.
    dp_engine = pipeline_dp.DPEngine(budget_accountant, backend)
    
    params = pipeline_dp.AggregateParams(
        noise_kind=pipeline_dp.NoiseKind.LAPLACE,
        metrics=[
            pipeline_dp.Metrics.COUNT, pipeline_dp.Metrics.SUM,
            pipeline_dp.Metrics.MEAN],
        max_partitions_contributed=1,
        max_contributions_per_partition=1,
        min_value=0,
        # Tips that are larger than 100 will be clipped to 100.
        max_value=100)
    # Specify how to extract privacy_id, partition_key and value from an
    # element of the taxi dataset.
    data_extractors = pipeline_dp.DataExtractors(
        partition_extractor=lambda x: x.taxi_id,
        privacy_id_extractor=lambda x: x.unique_key,
        value_extractor=lambda x: 0 if x.tips is None else x.tips)
    
    # Run aggregation.
    dp_result = dp_engine.aggregate(data, params, data_extractors)
    budget_accountant.compute_budgets()
    dp_result = backend.map_tuple(dp_result, lambda pk, result: (pk, result.count, result.sum, result.mean))
    return dp_result
    
    spark = SparkSession.builder.appName("spark-pipeline-dp-demo").getOrCreate()
    spark_context = spark.sparkContext
    
    # Load data from BigQuery.
    taxi_trips = spark.read.format("bigquery") \
    .option("table", "bigquery-public-data:chicago_taxi_trips.taxi_trips") \
    .load().rdd
    dp_result = compute_dp_metrics(taxi_trips, spark_context).toDF(["pk", "count","sum", "mean"])
    # Saving the data to BigQuery
    dp_result.write.format("bigquery") \
    .option("writeMethod", "direct") \
    .save("DATASET_ID.TABLE_NAME")
    """;
    

    Ersetzen Sie Folgendes:

    • PROJECT_ID: das Projekt, in dem Sie die gespeicherte Prozedur erstellen möchten.
    • DATASET_ID: das Dataset, in dem Sie die gespeicherte Prozedur erstellen möchten.
    • REGION: die Region, in der sich das Projekt befindet.
    • DOCKER_IMAGE: der Name des Docker-Images.
    • CONNECTION_ID: der Name der Verbindung.
    • TABLE_NAME: der Name der Tabelle.
  2. Verwenden Sie die Anweisung CALL, um die Prozedur aufzurufen.

    CALL `PROJECT_ID.DATASET_ID.pipeline_dp_example_spark_proc`()
    

    Ersetzen Sie Folgendes:

    • PROJECT_ID: das Projekt, in dem Sie die gespeicherte Prozedur erstellen möchten.
    • DATASET_ID: das Dataset, in dem Sie die gespeicherte Prozedur erstellen möchten.

Nächste Schritte