Hatena::ブログ(Diary)

ablog このページをアンテナに追加 RSSフィード

2018-09-16

AWS Glue の DynamicFrame と Spark の DataFrame の違い

Sparkとは

P.100

Apache Spark」も、MapReduce より効率の良いデータ処理を実現するプロジェクトとして開発が進められています。Hadoop の延長線上にある Tez とは異なり、Spark は Hadoop とは別の独立したプロジェクトです。Spark の特徴は大量のメモリを活用して高速化を実現することです。(中略)コンピュータが異常停止すると途中まで処理した中間データは消えてしまいますが、そのときには処理をやり直して、失われた中間データをま作れば良いというのが Spark の考え方です(図 3.8)。

(中略)

Spark は Hadoop を置き換えるものではなく、MapReduce を置き換える存在です。例えば、分散ファイルシステムである HDFS や、リソースマネージャである YARN などは、Spark からでもそのまま利用できます。Hadoop を利用しない構成も可能であり、分散ストレージとして Amazon S3 を利用したり、あるいは分散データベースである Cassandra からデータを読み込んだりするようなことも可能です。

f:id:yohei-a:20180916181231j:image:w640


Spark の歴史

P.5

Spark プロジェクトはもともとカリフォルニア大学バークレー校 AMPLab の研究プロジェクトとして2009年にスタートしました。BDAS(the Berkeley Data Analytics Stack)と呼ばれるビッグデータ分析のためのソフトウェアスタックがあり、Spark はそのコンポーネントのひとつに位置付けられています。Spark プロジェクトは2010年初頭にオープンソース化され、2013年6月に Apache Incubator Project に採択されて「Apache Spark」となりました。この頃から本格的な開発体制が整い始め、2013年10月には AMPLab から Spark 開発者がスピンアウトして、米 Databrics が設立されました。現在も Spark 開発者の多くは Databrics に所属しています。

AMPLAB is a University of California, Berkeley lab focused on Big data analytics. The name stands for the Algorithms, Machines and People Lab.[1][2] It has been publishing papers since 2008[3] and was officially launched in 2011.[4]

While AMPLab has worked on a wide variety of big data projects, many know it as the lab that invented Apache Spark.[5]

AMPLab - Wikipedia

f:id:yohei-a:20180916184431p:image:w640

About | AMPLab – UC Berkeley

DAG(Directed Acyclic Graph)とは

P.202-204

MapReduce に変わる新しいフレームワーク DAGによる内部表現

新しいフレームワークに共通するのがDAG(directed acyclic graph)と呼ばれるデータ構造です(図 5.12)。日本語では「有向非循環グラフ」と呼ばれます。DAG そのものは何かの技術ではなく、数学コンピュータアルゴリズムで用いられるデータモデルの一つです。DAG は、次のような性質を持ちます。

  • ノードノードが矢印で結ばれる(有向)
  • 矢印をいくら辿っても同じノードに戻らない(非循環)

データフローでは、実行すべき一連のタスクをDAGによるデータ構造として表現します。図中の矢印はタスクの実行順序を示しており、その依存関係を保ちながらうまく実行順序を決めることで、すべてのタスクを漏れなく完了させることができます。後は、これをどれだけ効率よく実行できるかという問題です。

従来の MapReduce も「Map」と「Reduce」の2種類のノードから成るシンプルなDAGであると考えることができます。ただし、一つのノードで処理が終わらなければ次の処理に進めないという非効率なものでした。

一方、データフローではDAGを構成する各ノードがすべて同時並行で実行されます。処理の終わったデータは、ネットワーク経由で次々と受け渡され、MapReduce にあった待ち時間をなくしています。


SparkにおけるDAG

DAGはシステムの内部的な表現であり、利用者がその存在を意識することはほとんどありません。データフローに限らず、Hive on Tez や Presto のようなクエリエンジンでもDAGは採用されており、SQLからDAGのデータ構造が内部で自動生成されています。一方、Spark のようなデータフローのフレームワークでは、プログラミング言語を用いてより直接的にDAGのデータ構造を組み立てます。

(中略)

DAGによるプログラミングの特徴が遅延評価(lazy evaluation)です。プログラムの各行は、実際にはDAGのデータ構造を組み立てているだけであり、その場では何の処理も行いません。まずはDAGを構築し、その後で明示的に、あるいは暗黙的に実行結果を要求することによって、ようやくデータ処理が開始されます。

MapReduceのようにMapやReduceを一つずつ実行するのではなく、最初にデータパイプライン全体をDAGとして組み立ててから実行に移すことで、内部のスケジューラが分散システムにとって効率の良い実行計画を建ててくれるのがデータフローの優れたところです。


RDDとは

P.14

Apache Spark のデータ処理には「RDD(Resilient Distributed Dataset)」と呼ばれるデータ構造を利用します。Spark のプログラミングモデルは「RDDを加工して新たなRDDを生成し、これを繰り返すことで目的の結果を得る」というものになっています。

(中略)

RDD は大量のデータを要素として保持する分散コレクションです。巨大な配列やリストのようなデータ構造を想像すると分かりやすいでしょう。RDD は複数のマシンから構成されるクラスタ上での分散処理を前提として設計されており、内部的にはパーティションというかたまりに分割されています。Spark では、このパーティション分散処理の単位となります。RDDパーティションごとに複数のマシンで処理することによって、単一のマシンでは処理しきれない大量のデータを扱うことができるのです。

ユーザーはたとえばHDFSなどの分散ファイルシステム上のファイルの内容を RDD にロードし、RDD を加工することで大量のデータの分散処理を実現できます。Spark ではこの加工に相当する処理を「変換」と呼びます。そして、RDD の内容を元に「アクション」と呼ばれる処理を適用して目的の結果を得るのです(図 2.2)。

このほかに、RDDイミュータブル(内部の要素の値を変更できない)ということと、生成や変換が遅延評価されるという性質があります。

f:id:yohei-a:20180916191822j:image:w640

D


DataFrame*1 とは

P.110

Spark SQL ではドライバプログラムからさまざまな形式のデータセットを統一的に扱うために、DataFrame と呼ばれる抽象的なデータ構造を用います。DataFrame とは RDBMS のテーブルのように行と名前とデータ型が付与された列の概念を持つデータ構造です。Spark SQL ではさまざまnあデータ型をサポートしており、Dataframe の列のデータ型に指定することができます。



DynamicFrame とは

  • AWS Glue でデータの抽出・変換をする際に使う Spark の DataFrame の Wrapper。
  • DynamicFrame は PythonScala 両方の API がある。
  • DataFrame は最初にスキーマ定義(列の型など)が必要で、同一列に型が異なる値があると String としてしか扱えないが、DynamicFrame だとスキーマ定義で読んだ上で型を揃えるなどの前処理ができる?
  • なので、DynamicFrame で前処理、DataFrame でSparkSQLで高度なAPIを使う、DynamicFrame に変換して書出しといった使い方になる?

参考

  • Python の DynamicFrame クラスの説明

DynamicFrame クラス

Apache Spark の主要な抽象化の 1 つは SparkSQL DataFrame で、これは R と Pandas にある DataFrame 構造に似ています。DataFrame はテーブルと似ており、機能スタイル (マップ/リデュース/フィルタ/その他) 操作と SQL 操作 (選択、プロジェクト、集計) をサポートしています。

DataFrames は、強力で広く使用されていますが、抽出、変換、およびロード (ETL) 操作に関しては制限があります。最も重要なのは、データをロードする前にスキーマを指定する必要があることです。SparkSQL は、データに対してパスを 2 つ作ることでこれを解決します。1 つ目はスキーマを推測し、2 つ目はデータをロードします。ただし、この推測は限定されており、実際の煩雑なデータには対応しません。たとえば、同じフィールドが異なるレコードの異なるタイプである可能性があります。Apache Spark は、多くの場合、作業を中断して、元のフィールドテキストを使用してタイプを string として報告します。これは正しくない可能性があり、スキーマの不一致を解決する方法を細かく制御する必要があります。また、大規模なデータセットの場合、ソースデータに対する追加パスが非常に高価になる可能性があります。

これらの制限に対応するために、AWS Glue により DynamicFrame が導入されました。DynamicFrame は、DataFrame と似ていますが、各レコードが自己記述できるため、最初はスキーマは必要ありません。代わりに、AWS Glue は必要に応じてオンザフライでスキーマを計算し、選択 (または共用) タイプを使用してスキーマの不一致を明示的にエンコードします。これらの不整合を解決して、固定スキーマを必要とするデータストアとデータセットを互換性のあるものにできます。

同様に、DynamicRecord は DynamicFrame 内の論理レコードを表します。これは、Spark DataFrame の行と似ていますが、自己記述型であり、固定スキーマに適合しないデータに使用できます。

スキーマの不一致を解決したら、DynamicFrames を DataFrames との間で変換することができます。

DynamicFrame クラス - AWS Glue
  • Scala の DynamicFrame の説明

DynamicFrame は、自己記述型の DynamicRecord オブジェクト分散コレクションです。

DynamicFrame は、ETL (抽出、変換、ロード) オペレーションの柔軟なデータモデルを提供するように設計されています。これらのオブジェクトを作成するのにスキーマは必要なく、乱雑または不整合な値や型を持つデータの読み取りと変換に使用できます。スキーマは、スキーマを必要とするオペレーションオンデマンドで計算できます。

DynamicFrame は、データクリーニングと ETL 用の広範な変換を提供します。また、既存のコードと統合するための SparkSQL DataFrames との相互変換や、DataFrames が提供する多くの分析オペレーションをサポートしています。

AWS Glue Scala DynamicFrame クラス - AWS Glue

GlueContext

The file context.py contains the GlueContext class. GlueContext extends PySpark's SQLContext class to provide Glue-specific operations. Most Glue programs will start by instantiating a GlueContext and using it to construct a DynamicFrame.

DynamicFrame

The DynamicFrame, defined in dynamicframe.py, is the core data structure used in Glue scripts. DynamicFrames are similar to Spark SQL's DataFrames in that they represent distributed collections of data records, but DynamicFrames provide more flexible handling of data sets with inconsistent schemas. By representing records in a self-describing way, they can be used without specifying a schema up front or requiring a costly schema inference step.

DynamicFrames support many operations, but it is also possible to convert them to DataFrames using the toDF method to make use of existing Spark SQL operations.

https://github.com/awslabs/aws-glue-libs/tree/master/awsglue

— Construction —

  • __init__
  • fromDF
  • toDF

(中略)

— Transforms —

  • apply_mapping
  • drop_fields
  • filter
  • join
  • map
  • relationalize
  • rename_field
  • resolveChoice
  • select_fields
  • spigot
  • split_fields
  • split_rows
  • unbox
  • unnest
  • write

(中略)

— Errors —

  • assertErrorThreshold
  • errorsAsDynamicFrame
  • errorsCount
  • stageErrorsCount
DynamicFrame Class - AWS Glue
# Copyright 2016-2017 Amazon.com, Inc. or its affiliates. All Rights Reserved.
# Licensed under the Amazon Software License (the "License"). You may not use
# this file except in compliance with the License. A copy of the License is
# located at
#
#  http://aws.amazon.com/asl/
#
# or in the "license" file accompanying this file. This file is distributed
# on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, express
# or implied. See the License for the specific language governing
# permissions and limitations under the License.

import json
from awsglue.utils import makeOptions, callsite
from itertools import imap, ifilter
from awsglue.gluetypes import _deserialize_json_string, _create_dynamic_record, _revert_to_dict, _serialize_schema
from awsglue.utils import _call_site, _as_java_list, _as_scala_option, _as_resolve_choiceOption
from pyspark.rdd import RDD, PipelinedRDD
from pyspark.sql.dataframe import DataFrame
from pyspark.serializers import PickleSerializer, BatchedSerializer


class ResolveOption(object):
    """
    ResolveOption is used for resolve ChoiceType while converting DynamicRecord to DataFrame
    option.action includes "Project", "KeepAsStruct" and "Cast".
    """
    def __init__(self, path, action, target=None):
        """
        :param path: string, path name to ChoiceType
        :param action: string,
        :param target: spark sql Datatype
        """
        self.path = path
        self.action = action
        self.target = target

参考

*1:SparkSQLの

2018-09-13

AWS Glue とは

カタログ

データベース
テーブル
分類子(Classifier)

ETL

ジョブ
トリガー
開発エンドポイント

セキュリティ


Apache Spark の主要な抽象化の 1 つは SparkSQL DataFrame で、これは R と Pandas にある DataFrame 構造に似ています。DataFrame はテーブルと似ており、機能スタイル (マップ/リデュース/フィルタ/その他) 操作と SQL 操作 (選択、プロジェクト、集計) をサポートしています。

DataFrames は、強力で広く使用されていますが、抽出、変換、およびロード (ETL) 操作に関しては制限があります。最も重要なのは、データをロードする前にスキーマを指定する必要があることです。SparkSQL は、データに対してパスを 2 つ作ることでこれを解決します。1 つ目はスキーマを推測し、2 つ目はデータをロードします。ただし、この推測は限定されており、実際の煩雑なデータには対応しません。たとえば、同じフィールドが異なるレコードの異なるタイプである可能性があります。Apache Spark は、多くの場合、作業を中断して、元のフィールドテキストを使用してタイプを string として報告します。これは正しくない可能性があり、スキーマの不一致を解決する方法を細かく制御する必要があります。また、大規模なデータセットの場合、ソースデータに対する追加パスが非常に高価になる可能性があります。

これらの制限に対応するために、AWS Glue により DynamicFrame が導入されました。DynamicFrame は、DataFrame と似ていますが、各レコードが自己記述できるため、最初はスキーマは必要ありません。代わりに、AWS Glue は必要に応じてオンザフライでスキーマを計算し、選択 (または共用) タイプを使用してスキーマの不一致を明示的にエンコードします。これらの不整合を解決して、固定スキーマを必要とするデータストアとデータセットを互換性のあるものにできます。

同様に、DynamicRecord は DynamicFrame 内の論理レコードを表します。これは、Spark DataFrame の行と似ていますが、自己記述型であり、固定スキーマに適合しないデータに使用できます。

DynamicFrame クラス - AWS Glue

上記のドキュメントでは、Crawlerがテーブルを作成する際はデータの先頭2MBを見て判断すると記載されています。

AWS GlueのDynamicFrameの動きを見てみる | Developers.IO

  • DPU

ETL ジョブの実行に使用された DPU (Data Processing Unit) の数に基づいて時間あたりの課金が発生します。1 つの DPU (Data Processing Unit) では 4 つの vCPU と 16 GB のメモリが提供されます。Glue の ETL ジョブには最低で 2 個の DPU が必要です。AWS Glue のデフォルトでは、各 ETL ジョブに 10 個の DPU が割り当てられます。DPU 時間あたり 0.44 ドルが 1 秒単位で課金され、最も近い秒単位に切り上げられます。ETL ジョブごとに 10 分の最小期間が設定されます。

AWS Glue の料金 ? アマゾン ウェブ サービス (AWS)
  • クローラー
    • DPU(データ処理ユニット)の時間単位で課金
    • 1DPU = 4vCPUと16GBメモリ
    • クローラーには2DPUが割り当て
    • 1DPU 0.44ドル/時
    • 最低10分とし、分単位で切り上げ請求
  • ETLジョブ
    • DPU(データ処理ユニット)の時間単位で課金
      • 1DPU = 4vCPUと16GBメモリ
      • Glue ETL処理には最低2DPUが必要
      • 本番環境のデフォルトはジョブごとに10DPUを割り当て
      • 開発エンドポイントのデフォルトは開発エンドポイントごとに5DPUを割り当て
    • 1DPU 0.44ドル/時
    • 最低10分とし、分単位で切り上げ請求
【新サービス】AWS上でフルマネージドなデータカタログとETLを実現するサービス『AWS Glue』がリリースされました!使い始めの準備をご紹介 | Developers.IO
  • Zeppelinとは

ブラウザ上でプログラムインタラクティブに記述できるノートブックというものを作成するツール一種です。 有名なところではJupyter notebook(IPython notebook)があるかと思いますが、それと似たツールだと想像していただければと思います。

Apache Zeppelin入門 | Hadoop Advent Calendar 2016 #19 | Developers.IO

ファイルの最初の方にデータの定義があり、その後にデータが連続して登録されています。jsonxmlのように定義名が何度も繰り返すような冗長さもなく、ファイルの最初を読み込んだ段階でデータ構造が理解できる「マシン・リーダブル」なフォーマット

(中略)

{
"name": "users",
"type": "record",
"fields": [
{"name": "id", "type": "int"},
{"name": "guid", "type": "string"},
{"name": "name", "type": "string"},
{"name": "address", "type": "string"}
]}
Amazon EMR の Avro フォーマットのデータを Amazon Redshift にロードする | Developers.IO

AWS Glue では、開発エンドポイントを作成してから、REPL (Read-Evaluate-Print Loop) シェルを呼び出して PySpark コードを増分的に実行し、ETL スクリプトデプロイする前にインタラクティブデバッグできるようにします。

チュートリアル: 開発エンドポイントで REPL シェルを使用する - AWS Glue

2018-09-12

「AWS Cloudtrail Logs を AWS Glue と Amazon Quicksight 使って可視化する」をやってみた

AWS Cloudtrail Logs を AWS Glue と Amazon Quicksight 使って可視化する | Amazon Web Services ブログ を試してみた。


Lambda用ロールの作成
  • 名前: CloudTrailWatchLogs
  • インラインポリシー
{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "logs:CreateLogGroup",
                "logs:CreateLogStream",
                "logs:PutLogEvents"
            ],
            "Resource": "arn:aws:logs:*:*:*"
        },
        {
            "Action": [
                "s3:*"
            ],
            "Resource": [
                "arn:aws:s3:::cloudtrail-do-not-delete/*",
                "arn:aws:s3:::cloudtrail-do-not-delete"
            ],
            "Effect": "Allow"
        }
    ]
}
Glue用ロールの作成
  • 名前: AWSGlueServiceRole-Default
  • 以下のポリシーをアタッチ
    • AmazonS3FullAccess
    • AWSGlueServiceRole
Lambda関数の作成
from __future__ import print_function
import json
import urllib
import boto3
import gzip

s3 = boto3.resource('s3')
client = boto3.client('s3')

def convertColumntoLowwerCaps(obj):
    for key in obj.keys():
        new_key = key.lower()
        if new_key != key:
            obj[new_key] = obj[key]
            del obj[key]
    return obj


def lambda_handler(event, context):

    bucket = event['Records'][0]['s3']['bucket']['name']
    key = urllib.unquote_plus(event['Records'][0]['s3']['object']['key'].encode('utf8'))
    print(bucket)
    print(key)
    try:
        newKey = 'flatfiles/' + key.replace("/", "")
        client.download_file(bucket, key, '/tmp/file.json.gz')
        with gzip.open('/tmp/out.json.gz', 'w') as output, gzip.open('/tmp/file.json.gz', 'rb') as file:
            i = 0
            for line in file: 
                for record in json.loads(line,object_hook=convertColumntoLowwerCaps)['records']:
            		if i != 0:
            		    output.write("\n")
            		output.write(json.dumps(record))
            		i += 1
        client.upload_file('/tmp/out.json.gz', bucket,newKey)
        return "success"
    except Exception as e:
        print(e)
        print('Error processing object {} from bucket {}. Make sure they exist and your bucket is in the same region as this function.'.format(key, bucket))
        raise e
Glue クローラの作成(Flatfile用)
  • 名前: cloudTrailFlatfiles
  • Choose a data store: S3
  • インクルードパス: s3://cloudtrail-do-not-delete/flatfiles
  • IAM ロール: AWSGlueServiceRole-Default
  • データベース: cloudtrail
  • 頻度: 毎時
Glue クローラの作成(Parquet用)
  • 名前: cloudtrailParquetFiles
  • Choose a data store: S3
  • インクルードパス: s3://cloudtrail-do-not-delete/parquettrails 
  • IAM ロール: AWSGlueServiceRole-Default
  • データベース: cloudtrail
  • 頻度: 毎時
Glueジョブの作成
import sys
from awsglue.transforms import *
from awsglue.utils import getResolvedOptions
from pyspark.context import SparkContext
from awsglue.context import GlueContext
from awsglue.job import Job
import boto3
import time

## @params: [JOB_NAME]
args = getResolvedOptions(sys.argv, ['JOB_NAME'])

sc = SparkContext()
glueContext = GlueContext(sc)
spark = glueContext.spark_session
job = Job(glueContext)
job.init(args['JOB_NAME'], args)

datasource0 = glueContext.create_dynamic_frame.from_catalog(database = "cloudtrail", table_name = "flatfiles", transformation_ctx = "datasource0")
resolvechoice1 = ResolveChoice.apply(frame = datasource0, choice = "make_struct", transformation_ctx = "resolvechoice1")
relationalized1 = resolvechoice1.relationalize("trail", args["TempDir"]).select("trail")
datasink = glueContext.write_dynamic_frame.from_options(frame = relationalized1, connection_type = "s3", connection_options = {"path": "s3://cloudtrail-do-not-delete/parquettrails"}, format = "parquet", transformation_ctx = "datasink4")
job.commit()
Athena でクエリ実行
select *
from cloudtrail.parquettrails
where eventtime > '2017-10-23T12:00:00Z' AND eventtime < '2017-10-23T13:00:00Z'
order by eventtime asc;

2018-09-04

Amazon Redshift で取得できる監査ログ

設定

監査ログの有効化

f:id:yohei-a:20180909190656p:image:w360

  • [監査ログ記録の設定]で以下の通り入力する
    • 監査ログ記録の有効化: はい
    • 監査ログ記録の有効化: 新規作成
    • 新規バケット名: redshift-trail-ds2xl2n(任意の名前)

f:id:yohei-a:20180909190654p:image:w360

ユーザーアクティビティログ取得設定
  • Redshift のパラメータグループを作成し enable_user_activity_logging を true に設定する。

f:id:yohei-a:20180909210817p:image

確認する

接続ログ

認証の試みと、接続および切断を記録します。次の表に、接続ログの情報を示します。

列名説明
event接続または認証イベント。
recordtimeイベントが発生した時刻。
remotehostリモートホストの名前または IP アドレス。
remoteportリモートホストのポート番号。
pidステートメントに関連付けられるプロセス ID。
dbnameデータベース名。
usernameユーザー名。
authmethod認証方法。
duration接続時間 (マイクロ秒)。
sslversionSecure Sockets Layer (SSL) バージョン。
sslcipherSSL 暗号。
mtu最大送信単位 (MTU)。
sslcompressionSSL 圧縮タイプ。
sslexpansionSSL 拡張タイプ。
  • 100000000000_redshift_ap-northeast-1_ds2xl2n_connectionlog_2018-09-04T07:16.gz
    • redshift-trail-ds2xl2n/AWSLogs/100000000000/redshift/ap-northeast-1/2018/09/04/
authenticated |Tue, 4 Sep 2018 06:16:36:393|::ffff:127.0.0.1 |53154 |13647|dev |rdsdb |password |0| | |0| | | |
initiating session |Tue, 4 Sep 2018 06:16:36:393|::ffff:127.0.0.1 |53154 |13647|dev |rdsdb |password |0| | |0| | | |
authenticated |Tue, 4 Sep 2018 06:19:30:621|::ffff:**.*.*.145 |25692 |13965|mydb |awsuser |password |0|TLSv1.2 |ECDHE-RSA-AES256-GCM-SHA384 |0| | | |
initiating session |Tue, 4 Sep 2018 06:19:30:621|::ffff:**.*.*.145 |25692 |13965|mydb |awsuser |password |0|TLSv1.2 |ECDHE-RSA-AES256-GCM-SHA384 |0| | | |
set application_name |Tue, 4 Sep 2018 06:19:30:621|::ffff:**.*.*.145 |25692 |13965|mydb |awsuser |password |159643|TLSv1.2 |ECDHE-RSA-AES256-GCM-SHA384 |0| | | |psql
disconnecting session |Tue, 4 Sep 2018 06:36:28:431|::ffff:**.*.*.145 |25692 |13965|mydb |awsuser |password |1017969825|TLSv1.2 |ECDHE-RSA-AES256-GCM-SHA384 |0| | | |psql
disconnecting session |Tue, 4 Sep 2018 06:36:36:366|::ffff:127.0.0.1 |53154 |13647|dev |rdsdb |password |1199973731| | |0| | | |

ユーザーログ

データベースユーザーに対する操作を記録する。

  • ユーザーの作成
  • ユーザーの削除
  • ユーザーの変更 (名前の変更)
  • ユーザーの変更 (プロパティの変更)
列名説明
userid変更の影響を受けるユーザーの ID。
username変更の影響を受けるユーザーのユーザー名。
oldusername名前の変更アクションの場合、以前のユーザー名。その他のアクションの場合、このフィールドは空です。
action実行されたアクション。有効な値: Alter 作成 Drop Rename
usecreatedbtrue (1) の場合、ユーザーに create database 権限があることを示します。
usesupertrue (1) の場合、ユーザーがスーパーユーザーであることを示します。
usecatupdtrue (1) の場合、ユーザーはシステムカタログを更新できることを示します。
valuntilパスワードが失効する日付。
pidプロセス ID。
xidトランザクション ID。
recordtimeUTC で表されたクエリの開始時間。

ユーザーアクティビティログ

クエリ実行単位のログ

列名説明
recordtimeイベントが発生した時刻。
dbデータベース名。
ユーザーユーザー名。
pidステートメントに関連付けられるプロセス ID。
useridユーザー ID
xidトランザクション ID。
queryプレフィックス LOG の後に、改行を含むクエリのテキストが続きます。
  • 100000000000_redshift_ap-northeast-1_ds2xl2n_useractivitylog_2018-09-04T06:16.gz
    • redshift-trail-ds2xl2n/AWSLogs/100000000000/redshift/ap-northeast-1/2018/09/04/
'2018-09-04T05:34:50Z UTC [ db=mydb user=awsuser pid=9972 userid=100 xid=7200 ]' LOG: select * from STL_USERLOG;
'2018-09-04T05:34:50Z UTC [ db=mydb user=awsuser pid=9972 userid=100 xid=7200 ]' LOG: SELECT pg_catalog.stl_userlog.userid AS userid, pg_catalog.stl_userlog.username AS username, pg_catalog.stl_userlog.oldusernam
e AS oldusername, pg_catalog.stl_userlog.action AS action, pg_catalog.stl_userlog.usecreatedb AS usecreatedb, pg_catalog.stl_userlog.usesuper AS usesuper, pg_catalog.stl_userlog.usecatupd AS usecatupd, pg_catalog
.stl_userlog.valuntil AS valuntil, pg_catalog.stl_userlog.pid AS pid, pg_catalog.stl_userlog.xid AS xid, pg_catalog.stl_userlog.recordtime AS recordtime FROM pg_catalog.stl_userlog;



参考

2018-07-07

コンテナ について

コンテナという言葉の意味

container

con-「共に」tain「つかんで離さない」-er「人、もの」

->何かをとどめようとするもの

-> 【名】入れもの、コンテナ

英単語 container の語源と意味 - Gogengo! - 英単語は語源でたのしく

コンテナ (英: container)とは、内部に物を納めるための容器のことである。コンテナーとも呼ばれる。

コンテナ - Wikipedia

コンピュータにおけるコンテナ

 商用OSの世界でも、SolarisゾーンやHP-UX Containersなどのように、コンピュータ資源を分離する「コンテナ技術」が発展していきました。ここで、コンテナという言葉が出てきます。コンテナとは船や列車などの貨物輸送で使われる容器です。一隻に大量のコンテナを積載して運ぶ貨物輸送船を思い浮かべて下さい。

 なぜ貨物でコンテナが利用されるのでしょう。容器を直方体の箱にすれば船の限られたスペースにすき間なく積み上げて効率よく配置でき、異なる種類のコンテナ同士で内容物が混ざるといったトラブルも避けられます。依頼主にも管理側にもメリットがあるからです。

 この「隙間なく積み上げて配置できること」と「内容物が混ざるトラブルが発生しないこと」という点が非常に重要です。コンピュータにおけるコンテナも同じ考え方です。コンピュータにおいて、一隻のコンテナ船はホストOSです。その上に載る大量のコンテナの群れには、それぞれさまざまなアプリのプロセスが稼働しています。隙間なく積まれたコンテナの群れをよく目を凝らしてみてみると、コンテナ同士はぴったりとくっついて配置されていますが、お互いのコンテナは、となりのコンテナの内容物(プロセス)は知り得ません。すなわち、ホストOSであるコンテナ船から見た人は、コンテナという分離された空間がいくつも存在するかのように見えます。これが、分離された空間=コンテナと呼ばれるゆえんです。

 また、船の平らな甲板にコンテナが直接触れて置かれている点も重要です。平らであるということをコンピュータに置き換えると、ホストOSとコンテナが直接触れているということは、ホストOSとコンテナの間にはハイパーバイザーのような介在者がいないことになります。すなわち、コンテナで稼働するアプリのプロセスは、ホストOSから直接起動されているのです。

第4回 「Dockerのクジラロゴ」が意味するもの (2/3) - ITmedia エンタープライズ

他の仮想化とコンテナの違い


コンテナの歴史

f:id:yohei-a:20180708124417p:image:w640

chroot が生まれた背景

 一般的にアプリなどの稼働テストにおいて、実際の本番環境のファイルなどを直接作成、変更、削除するのは、非常に危険です。chroot監獄は、このような本番環境で試すと危険をともなう場合と比べ、ソフトウェアの開発やテスト環境を安全に行うことができます。当時は非力な計算機を使って、BSDなどのUNIX向けにさまざまなソフトウェアの開発が研究機関において行われていました。このような「監獄」の考え方が出現したのは、ソフトウェア開発者が1台のマシンで本番環境をシミュレートして、効率的にかつ安定的に開発を行いたいというニーズが背景にあったためです。

f:id:yohei-a:20180708124941j:image

本番機と開発機を2重に持たず、本番機で開発するのは非常に危険。そこで、本番用のファイルシステムの一部を分離(隔離)するという考えが生まれた

第1回 Dockerと「昭和54年」の深〜い関係 - ITmedia エンタープライズ
chroot の応用例

chroot監獄は開発の場面だけでなく、システムファイルの破損や、操作ミスなどで誤ってファイルを削除してしまい、OSが起動不能になった場合に、インストールメディアのレスキューモードを使ってOSを復旧させるシーンにおいても使われています。

 具体的には、インストールメディアで対象となるマシンを起動後、破損したOSのルートディレクトリを適当な名前のディレクトリ(/mnt/sysimageなど)にマウントすることに成功すれば、そのディレクトリにchrootを実行することで、破損したOSのルートディレクトリに遷移できます。これにより、起動不能だったOSのコマンド群を使えるようになり、復旧作業を行うことができます。

 また、セキュリティの面においても「ハニーポット(蜜の壺/おとりサーバ)」と呼ぶクラッカー対策にchrootが利用されます。現在(2015年)では、chrootを使ったハニーポットに代わる新しいセキュリティ対策の仕組みがいろいろと研究されていますが、基本的にはchrootの考え方を踏襲しており、2015年現在でもフリーOSなどで利用されています。

f:id:yohei-a:20180708125240j:image

chrootの応用例。chrootのファイルシステムの分離機能はソフトウェアの開発だけでなく、さまざまな分野で応用されている

第1回 Dockerと「昭和54年」の深〜い関係 - ITmedia エンタープライズ
FreeBSD Jail

2000年、オープンソース界隈であるホットなニュースが飛び交いました。

 chroot監獄を大幅に発展させた機能が、フリーOSで利用可能となったのです。その名も「FreeBSD Jail(フリー・ビーエスディ・ジェイル)」です。「あるディレクトリ配下をルートディレクトリに見せる」というファイルシステムを取り扱う概念に加え、さらにアプリのプロセスIDも監獄ごとに分離できるようになりました。

 このFreeBSD Jailは、監獄の中からホストOS側を見ると、ホストOSの各種資源の一部分だけがあたかもすべての資源のように見せることができる画期的なものです。FreeBSD Jailはとても軽く、洗練されたアーキテクチャとして知られており、日本やロシアで根強い人気があるFreeBSDと呼ばれるBSD系のフリーOSにおける強力なOS空間の分離機能として発展し、2015年現在でも広く利用されています。

 その後FreeBSD Jailは、VIMAGEと呼ぶネットワークに関する分離機能も追加されました。

第4回 「Dockerのクジラロゴ」が意味するもの (1/3) - ITmedia エンタープライズ
Dockerが生まれた背景

Googleでのコンテナ

つまり私たちが利用するGoogleのすべてのサービスも、Googleの社内で使われているツールもすべて、すでにGoogleではDockerのようなコンテナ型仮想化技術の上で実行されているということのようです。

「We start over 2billion containers per week.」(私たちは毎週20億個以上のコンテナを起動している)とも書いてあり、Google内部ではすさまじい数のコンテナが実稼働していることになります。

いまDockerを中心にコンテナ型仮想化が話題になっていますが、Googleではすでにコンテナがあたりまえの技術になっている、ということなのでしょう。

no title

Fargate

f:id:yohei-a:20180708132118p:image:w640

f:id:yohei-a:20180708132124p:image:w640

f:id:yohei-a:20180708132112p:image:w640


Kubernetes

Kubernetesとは

Kubernetesはオープンソースの「コンテナオーケストレーション」ツールです。公式サイトのトップページにおいてもそう明示されていますが、「コンテナオーケストレーション」には明確な定義がまだありません。そこで本連載では、コンテナオーケストレーションを「コンテナ型仮想化を本番環境で活用するために必要な機能を提供すること」と定義します。

(中略)

Kubernetesの起源

Kubernetesの起源をたどる際には、Googleのエンジニアが執筆したサービス管理に関する有名な論文が参考になります。この論文では、「Googleのサービスは、クラスタマネジャー『Borg』上で動作するコンテナを用いて提供されており、Borgと同様の仕組み(+Borgにおける反省を踏まえた対応策)を備えたオープンソースソフトウェアとしてKubernetesを開発した」旨が記載されています。

Googleのサービスを支えている基盤と同様の仕組みを備えていることから、「KubernetesはGoogleで既にその有効性を実証済みである」という意味で大きな注目を浴びたといえるでしょう。

「Kubernetes」とは何か――コンテナ型仮想化の本番利用に向けた課題:先行事例に学ぶKubernetes企業活用の現実(1) - @IT

Kubernetesは要するに、プロセッシングのリソース管理の問題などを解決するためのオーケストレーションソフトウェアです。

プロセッシングだとか、ハイアベイラビリティだとかを。Kubernetesと、あとKubernetesが動作の前提とするEtcdという分散キーバリューストアをペアにして解決していくというものになりますが。

no title

EKS


参考

  • コンテナの性能分析

2011年7月1日

米国の新興クラウドベンダである「DotCloud」が、ベータ期間を終了し、正式サービスを開始しました。

DotCloudの最大の特徴は、PHPやPerl、Ruby、JavaPython、Node.jsなど複数の言語と、MySQL、PostgreSQL、Cassandra、MongoDB、CouchDB、Redisなど複数のデータベースやMemcached、RabbitMQ、Hadoopなどのさまざまなソフトウェアを開発者が自由に組み合わせてプラットフォームを構成することができ、それがクラウド上のPaaSとして提供されるという点です。

(中略)

元シックスアパートの宮川達彦氏が、4月にDotCloudへ転職したことをブログで明らかにしていますが、そのエントリで宮川氏はこのように書いています。

I hope to see Perl deployments beat Ruby and Node.js on DotCloud some day :)

クラウド上の言語としてPerlが使えるプラットフォームはこれまでほとんどありませんでした。果たして、新しい世代のPaaSではどのような言語やデータベースが主流となるのでしょうか?

プログラミング言語やデータベースが選べる新世代PaaS「DotCloud」が正式サービス開始

1番のポイントは、PDBがいくつあってもインスタンスは1つだけというところです。PDBごとにメモリやプロセスを割り当てていたのでは、従来型のデータベースを複数作成する場合と同じで無駄なリソースを多く使用してしまいます。インスタンスを各PDBが共同利用することで、リソースを節約しようというのがOracle Multitenantの考え方なのです。こうして集約率を高め、さらにPDBとして独立性を持たせることで、スキーマ名の競合やセキュリティの見直しといった統合にありがちな課題まで、まとめて解決することができます。

徹底解説!Oracle Database 12cのすべて Vol.1 | アシスト

Webコンテナ(ウェブコンテナ、Web container)とは、Java Platform, Enterprise Edition (Java EE) アーキテクチャのWebコンポーネント規約を実装するソフトウェア[1]。Java Servletの実行環境となることからServletコンテナ(サーブレットコンテナ、Servlet container)とも呼ばれる。

この規約では、コンピュータセキュリティ、並列性、ライフサイクル管理、トランザクション処理、デプロイやその他のサービスを含むWebコンポーネントの実行環境を規定している。WebコンテナはJava EEプラットフォームAPIを利用したJSPコンテナとしての機能も提供する。

Webコンテナ - Wikipedia
  • コントロールプレーン/データプレーンの語源

データプレーン、コントロールプレーン

Docker container networking:overlay networkで出て来る。

Dockerのネットワークを理解するためのネットワーク技術入門 – PAYFORWARD

Docker EE networking features

The following two features are only possible when using Docker EE and managing your Docker services using Universal Control Plane (UCP):

Docker container networking:overlay network

上のスライドの黒塗り箇所が YouTube では見れる