[CSS] SVGの使い方

SVGとは
– XMLをベースにした二次元ベクターデータ

SVGのメリット
– 拡大・縮小に強い
– 軽い
– CSSで装飾させたりアニメーションも可

デメリット
– 写真やイラスト等に向かない

### SVG作成
まずPhotoshopでSVG画像を作ります

あれ、保存できない。。
というか、SVGはillustratorで作るらしい。 なるほど。。。。

気を取り直して、illustratorで画像を作ります。

保存した状態

sublimeに当ててみると。。。

<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 23.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0)  -->
<svg version="1.1" id="レイヤー_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px"
	 y="0px" viewBox="0 0 500 500" style="enable-background:new 0 0 500 500;" xml:space="preserve">
<style type="text/css">
	.st0{fill:none;}
	.st1{font-family:'KozGoPr6N-Regular-83pv-RKSJ-H';}
	.st2{font-size:261px;}
</style>
<rect x="14" y="106.68" class="st0" width="478" height="269.86"/>
<text transform="matrix(1 0 0 1 14 336.3662)" class="st1 st2">SVG</text>
</svg>

ほう、こんなんなってるのか。

	<h1>SVG</h1>
	<img src="/img/sample.svg">

### css表示

<div class="test"></div>
.test {
	background-image: url("img/sample.svg");
}

– fill, fill-opacity, stroke, stroke-width, stroke-dasharray, stroke-dashoffsetなど使用可能

### objectで表示

<object type="image/svg+xml" data="/img/sample.svg" width="200" height="100"></object>

### fillの例

	<svg id="test" xmlns="http://www.w3.org/2000/svg">
		<circle class="icon" cx="50" cy="50" r="50"/>
	</svg>
#test {
	fill: red;
}

[position:fixed;] ヘッダー固定

<body>
<div class="wrapper">
	<header>
		<h1 class="headline">
			<a href="">Sample</a>
		</h1>
		<ul class="nav-list">
			<li class="nav-list-item"><a href="">Home</a></li>
			<li class="nav-list-item"><a href="">About</a></li>
			<li class="nav-list-item"><a href="">Topic</a></li>
		</ul>
	</header>
	<div class="main">
	<img src="butterfly.jpg">
	<h1>Butterfly</h1>
	<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.</p>
	<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.</p>

	</div>
	<footer>
		<ul class="footer-menu">
			<li>home |</li>
			<li>about |</li>
			<li>service |</li>
			<li>Contact Us</li>
		</ul>
		<p>&copy; All rights reserved by Sample</p>
	</footer>
</div>
</body>
* {
	margin:0; padding:0;
}
.wrapper {
	min-height: 100vh;
	position:relative;
	padding-bottom: 120px;
	box-sizing: border-box;
}
header {
	height: 100px;
	width: 100%;
	padding: 15px 0;
	background-color: #337079;
	color: white;
	margin-top: 0px;
	position: fixed;
}
header .headline {
	line-height: 100px;
	float: left;
	font-size: 30px;
	margin-left: 100px;
}
.nav-list {
	line-height: 100px;
	float: left;
	margin-left: 30px;
	list-style:none;
}
.nav-list-item {
	list-style: none;
	display: inline-block;
	margin: 0 20px;
}
.main {
	width: 80vw;
	padding-top: 170px;
	margin: 0px auto;
}
footer {
	width: 100%;
	height: 100px;
	background-color: #cab64a;
	color: #fff;
	text-align: center;
	position: absolute;
	bottom:0;
}
ul.footer-menu li {
	display: inline;
}

レポジトリに登録しておこう。

[position:relative;] footer下固定

<!DOCTYPE html>
<html lang="en">
<head>
	<meta charset="UTF-8">
	<meta name="viewport" content="width=device-width, initial-scale=1.0">
	<link rel="stylesheet" href="layout.css">
	<title>Document</title>
</head>
<body>
<header>
	<h1 class="headline">
		<a href="">Sample</a>
	</h1>
	<ul class="nav-list">
		<li class="nav-list-item"><a href="">Home</a></li>
		<li class="nav-list-item"><a href="">About</a></li>
		<li class="nav-list-item"><a href="">Topic</a></li>
	</ul>
</header>
	<footer>
		<ul class="footer-menu">
			<li>home |</li>
			<li>about |</li>
			<li>service |</li>
			<li>Contact Us</li>
		</ul>
		<p>&copy; All rights reserved by Sample</p>
	</footer>
</body>
</html>
* {
	margin:0; padding:0;
}
header {
	height: 100px;
	width: 100%;
	padding: 15px 0;
	background-color: #337079;
	color: white;
}
header .headline {
	line-height: 100px;
	float: left;
	font-size: 30px;
	margin-left: 100px;
}
.nav-list {
	line-height: 100px;
	float: left;
	margin-left: 30px;
	list-style:none;
}
.nav-list-item {
	list-style: none;
	display: inline-block;
	margin: 0 20px;
}
footer {
	width: 100%;
	height: 100px;
	background-color: #cab64a;
	color: #fff;
	text-align: center;
}
ul.footer-menu li {
	display: inline;
}

.wrapper {
	min-height: 100vh;
	position:relative;
	padding-bottom: 120px;
	box-sizing: border-box;
}

footer {
	width: 100%;
	height: 100px;
	background-color: #cab64a;
	color: #fff;
	text-align: center;
	position: absolute;
	bottom:0;
}

意外とするできる。

[Google Analytics API] PHPでリアルタイムユーザ数を取得して表示する

GA APIでページビューやセッションだけでなく、rt:activeUsersでリアルタイムユーザを取得できる。

require_once '../google-api-php-client/src/Google/autoload.php';
$service_account_email = '*.iam.gserviceaccount.com';
$key = file_get_contents('*.p12');
$profile = '*';

$client = new Google_Client();
$analytics = new Google_Service_Analytics($client);

$cred = new Google_Auth_AssertionCredentials(
  $service_account_email,
  array(Google_Service_Analytics::ANALYTICS_READONLY),
  $key
);

$client->setAssertionCredentials($cred);
if($client->getAuth()->isAccessTokenExpired()){
  $client->getAuth()->refreshTokenWithAssertion($cred);
}

$optParams = array(
'dimensions' => 'rt:medium');

try {
$results = $analytics->data_realtime->get(
  'ga:' . $profile,
  'rt:activeUsers',
  $optParams);
} catch (apiServiceException $e) {
  $error = $e->getMessage();
}
print("<pre>");
// print_r($results["totalsForAllResults"]["rt:activeUsers"]);
print_r($results);
print("</pre>");

$array[“totalsForAllResults”][“rt:activeUsers”] でアクティブユーザすうを取れるが、配列で何が取れるか確認した方が良い。

GAの場合、analytics.jsでajaxで処理しているので、ELBのアクセスログから例えば過去5分間のアクセス数を数えてログインユーザとして表示するってよりは、GA APIの方が現実的か。

ちなみに、rtって、リツイートの略かと思ったけど、real timeの略っぽいね。なんじゃそりゃw

[CSS] cssでのvwとは?

cssの中でvwってよく見ますが、vwって何でしょう?
vw: viewport width -> 幅に対する割合、100がマックス
vh: viewport height -> 高さに対する割合

	<style>
		img {
			display: inline-block;
			margin:auto;
			width: 50vw;
		}
	</style>
	<div class="container">
		<img src="/img/test.jpg">
	</div>

フォルクスワーゲンの事じゃないのね。。
VW、cssまで進出して凄いと思ってたが、違った様だ。

[CSS] transitionとは

CSSトランジションとは、CSSプロパティが変化する際のアニメーション速度を操作する

	<style>
		.sample {
			border: 1px solid #ccc;
			border-radius: 5px;
			width: 150px;
			height: 60px;
			line-height: 60px;
			font-weight: bold;
			text-align: center;
			color: green;
			box-shadow: 20px 10px 2px #8D9EB8;
			transition: 0.5s;
		}
		.sample:hover {
			color: orange;
			box-shadow: -20px 10px 5px #8D9EB8;
		}
	</style>
	<div class="container">		
		<div class="sample">Sample</div>		
	</div>

transitionの値を2sとか0.5sとか変えると、動きも変わる。

なるほど、アニメーションの動きは、ここで制御しとるんか。

_notesとdwsync.xml

_notesとdwsync.xmlは?
-> Dreamweaverがファイル同士の同期情報を管理する為のファイル
-> ファイルとGET/PUTするときに双方のタイムスタンプを見比べて、上書きの警告・チェックをする役割を持つ

確かにdwsync.xmlの中身を見ると、数字が入ってますね。ただ、Unixタイムスタンプとは別の値の様です。

local="*" remote="*"

なるほど、面倒だけど、一つ一つ調べるべきだな。

[Laravel8.x] リリース前に特定のipのみログインできる様にする

リリース前にテストを行う場合に、特定のipからのアクセスのみログインできる様にしたい

$request->ip();でipを取得できる

    public function test(Request $request){
        $ip = [
            ['name'=>'a社 事業部', 'ip' => '127.0.0.1'],
            ['name'=>'a社 開発部', 'ip' => '127.0.0.2'],
            ['name'=>'b社', 'ip' => '127.0.0.3'],
            ['name'=>'myIP', 'ip' => '192.168.33.1'],
        ];
        
        $user_ip = $request->ip();
        $detect = collect($ip)->contains('ip', $request->ip());
        dd($detect);
        
        return view('admin.test');
    }

-> true

これをmiddlewareのrole_idの制御しているところで実装する。

    public function handle(Request $request, Closure $next)
    {
        
        
        $user = Auth::user();
        if(!$user->isAdmin()){

            $ip = [
                ['name'=>'a社 事業部', 'ip' => '127.0.0.1'],
                ['name'=>'a社 開発部', 'ip' => '127.0.0.2'],
                ['name'=>'b社', 'ip' => '127.0.0.3'],
                ['name'=>'myIP', 'ip' => '192.168.33.1'],
            ];
            
            $user_ip = $request->ip();
            $detect = collect($ip)->contains('ip', $request->ip());

            if(!$detect){
                Auth::logout();
                return redirect('/login')->withErrors(array('name' => 'ただ今ログインできません。'));    
            }
            return redirect()->intended('/hoge');
        }
        return $next($request);
    }

-> ただ今ログインできません。

なかなかテクニカルになってきた。

[Laravel8.x] bcryptのストレッチングが10以外のパスワードでログインする

まずストレッチング10で”hogehogehoge”をbcryptします。
$2y$10$duXTr3ecMQZQUF6P3HWHWuZzRdZvS5AORbZuCLcID3qjqk1ZZLUja
mysql> update users set password=”$2y$10$duXTr3ecMQZQUF6P3HWHWuZzRdZvS5AORbZuCLcID3qjqk1ZZLUja” where name=”user1″;

これでログインします。

はい、当然ログインできます。
続いて、ストレッチングを12に上げます。
$2y$12$DM/DSh2iH9SYRYXHZRlIpuGvIUjBiehKuAuoGhq4cnCrQ.SZbc/Fa
mysql> update users set password=”$2y$12$DM/DSh2iH9SYRYXHZRlIpuGvIUjBiehKuAuoGhq4cnCrQ.SZbc/Fa” where name=”user1″;

あ、round12でもログインできますね。

round8
$2y$08$qEswpql7zOBs6UleOBC.2uyw3qzsInlrVXTq/oCdFcWpOqVlRU0/C
ストレッチング8(2^8)でも問題なく入れます。

Bcryptとは

Bcryptとは?
– Blowfish暗号を基盤としたパスワードハッシュアルゴリズム
– 一般にパスワードは一方向性関数の性質を持つハッシュ関数を用い値ハッシュ値で保管する

ハッシュする際に、ソルトとストレッチングを実施する

ソルトとは
-> パスワードに付与するランダムな文字列
-> レインボーテーブル攻撃だと、ソルトが付与されているハッシュ値だと推測できない
-> ソフトはユーザ毎にランダムな値で生成することが望ましいとされている

ストレッチング
-> ハッシュ関数を用いてハッシュ値への計算を数千回〜数万回繰り返し実施
弱いパスワードや文字数が長くないパスワードは総当たり攻撃(ブルートフォース攻撃)などで時間をかければ元のデータを推測されてしまう可能性がある

“hogehogehoge”をbcryptでハッシュ化してみる
$2y$10$WjqfZuhkX4nwfkdlB0Itxu.Vr2EcIcNJlGbhkyOVfWDhtCO9zMSSa
$2yはハッシュアルゴリズムのバージョンを示す。2, 2a, 2b, 2x, 2yなどがある
$10はストレッチングの回数

ソルト(22文字)
ストレッチング回数の後の128ビット(22文字)がソルト
ソルトの後の184ビット(31文字)は結果のハッシュ値

なるほどどういう仕組みか大まかな概要は理解した。
ストレッチングの回数を変更してもアルゴリズムは変わらないはずだから、phpのbcrypt(password_hash)のストレッチングが10(2の10乗で1024回)でも12(2の12乗)でも元が同じならログインできるでOK?