Compare commits
45 Commits
develop
...
tag-auto-c
Author | SHA1 | Date | |
---|---|---|---|
![]() |
5c0aea50d7 | ||
![]() |
7bcf48c8bf | ||
![]() |
8f1a94b863 | ||
![]() |
1b54af63ce | ||
![]() |
3ba946ec11 | ||
![]() |
32e25a9f7a | ||
![]() |
31626f48d9 | ||
![]() |
174d802edf | ||
![]() |
9c9db69662 | ||
![]() |
8c5fdfb7f8 | ||
![]() |
c616800da1 | ||
![]() |
6449094b78 | ||
![]() |
072b3a0910 | ||
![]() |
83d22b807f | ||
![]() |
914d92e545 | ||
![]() |
dcef270790 | ||
![]() |
5808ac58ee | ||
![]() |
b60932b6c5 | ||
![]() |
28520007e4 | ||
![]() |
63af49ba70 | ||
![]() |
3825228344 | ||
![]() |
855011c624 | ||
![]() |
bb7b05435e | ||
![]() |
5c26e58c1d | ||
![]() |
ddb11ee96c | ||
![]() |
38c7755757 | ||
![]() |
c0cfbe1bc4 | ||
![]() |
96bf90104e | ||
![]() |
2bcd050fed | ||
![]() |
ea1483a90a | ||
![]() |
7e7d0f80c1 | ||
![]() |
32398fea73 | ||
![]() |
076e7d5d0d | ||
![]() |
41c7679423 | ||
![]() |
486e5bad0a | ||
![]() |
a026897986 | ||
![]() |
96658ac34c | ||
![]() |
622964ec01 | ||
![]() |
141067beab | ||
![]() |
61b83c18a7 | ||
![]() |
581ae56173 | ||
![]() |
b50a15c109 | ||
![]() |
060bdeef43 | ||
![]() |
be098c38cb | ||
![]() |
d7d2bc2397 |
@@ -24,6 +24,7 @@ commands:
|
||||
- checkout
|
||||
- run: sudo apt update
|
||||
- run: sudo apt install -y libpq-dev
|
||||
- run: sudo pecl install -f xdebug-2.9.8 && sudo docker-php-ext-enable xdebug
|
||||
- run: sudo docker-php-ext-install zip
|
||||
- run: sudo docker-php-ext-install pdo_pgsql
|
||||
- run:
|
||||
|
@@ -10,7 +10,6 @@ RUN apt-get update \
|
||||
&& pecl install xdebug \
|
||||
&& curl -sS https://getcomposer.org/installer | php \
|
||||
&& mv composer.phar /usr/local/bin/composer \
|
||||
&& composer global require hirak/prestissimo \
|
||||
&& sed -ri -e 's!/var/www/html!${APACHE_DOCUMENT_ROOT}!g' /etc/apache2/sites-available/*.conf \
|
||||
&& sed -ri -e 's!/var/www/!${APACHE_DOCUMENT_ROOT}!g' /etc/apache2/apache2.conf /etc/apache2/conf-available/*.conf \
|
||||
&& a2enmod rewrite
|
||||
|
@@ -19,7 +19,7 @@ class Ejaculation extends Model
|
||||
protected $fillable = [
|
||||
'user_id', 'ejaculated_date',
|
||||
'note', 'geo_latitude', 'geo_longitude', 'link', 'source',
|
||||
'is_private', 'is_too_sensitive',
|
||||
'is_private', 'is_too_sensitive', 'discard_elapsed_time',
|
||||
'checkin_webhook_id'
|
||||
];
|
||||
|
||||
@@ -105,4 +105,33 @@ class Ejaculation extends Model
|
||||
'is_too_sensitive' => $this->is_too_sensitive,
|
||||
]);
|
||||
}
|
||||
|
||||
public function ejaculatedSpan(): string
|
||||
{
|
||||
if (array_key_exists('ejaculated_span', $this->attributes)) {
|
||||
if ($this->ejaculated_span === null) {
|
||||
return '精通';
|
||||
}
|
||||
if ($this->discard_elapsed_time) {
|
||||
return '0日 0時間 0分'; // TODO: 気の効いたフレーズにする
|
||||
}
|
||||
|
||||
return $this->ejaculated_span;
|
||||
} else {
|
||||
$previous = Ejaculation::select('ejaculated_date')
|
||||
->where('user_id', $this->user_id)
|
||||
->where('ejaculated_date', '<', $this->ejaculated_date)
|
||||
->orderByDesc('ejaculated_date')
|
||||
->first();
|
||||
|
||||
if ($previous === null) {
|
||||
return '精通';
|
||||
}
|
||||
if ($this->discard_elapsed_time) {
|
||||
return '0日 0時間 0分';
|
||||
}
|
||||
|
||||
return $this->ejaculated_date->diff($previous->ejaculated_date)->format('%a日 %h時間 %i分');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -35,6 +35,7 @@ class WebhookController extends Controller
|
||||
'tags.*' => ['string', 'not_regex:/[\s\r\n]/u', 'max:255'],
|
||||
'is_private' => 'nullable|boolean',
|
||||
'is_too_sensitive' => 'nullable|boolean',
|
||||
'discard_elapsed_time' => 'nullable|boolean',
|
||||
], [
|
||||
'tags.*.not_regex' => 'The :attribute cannot contain spaces, tabs and newlines.'
|
||||
]);
|
||||
@@ -71,6 +72,7 @@ class WebhookController extends Controller
|
||||
'source' => Ejaculation::SOURCE_WEBHOOK,
|
||||
'is_private' => (bool)($inputs['is_private'] ?? false),
|
||||
'is_too_sensitive' => (bool)($inputs['is_too_sensitive'] ?? false),
|
||||
'discard_elapsed_time' => (bool)($inputs['discard_elapsed_time'] ?? false),
|
||||
'checkin_webhook_id' => $webhook->id
|
||||
]);
|
||||
|
||||
|
@@ -23,6 +23,7 @@ class EjaculationController extends Controller
|
||||
|
||||
$errors = $request->session()->get('errors');
|
||||
$initialState = [
|
||||
'mode' => 'create',
|
||||
'fields' => [
|
||||
'date' => old('date') ?? $request->input('date', date('Y/m/d')),
|
||||
'time' => old('time') ?? $request->input('time', date('H:i')),
|
||||
@@ -30,7 +31,9 @@ class EjaculationController extends Controller
|
||||
'tags' => $tags,
|
||||
'note' => old('note') ?? $request->input('note', ''),
|
||||
'is_private' => old('is_private') ?? $request->input('is_private', 0) == 1,
|
||||
'is_too_sensitive' => old('is_too_sensitive') ?? $request->input('is_too_sensitive', 0) == 1
|
||||
'is_too_sensitive' => old('is_too_sensitive') ?? $request->input('is_too_sensitive', 0) == 1,
|
||||
'is_realtime' => old('is_realtime', true),
|
||||
'discard_elapsed_time' => old('discard_elapsed_time') ?? $request->input('discard_elapsed_time') == 1,
|
||||
],
|
||||
'errors' => isset($errors) ? $errors->getMessages() : null
|
||||
];
|
||||
@@ -43,15 +46,20 @@ class EjaculationController extends Controller
|
||||
$inputs = $request->all();
|
||||
|
||||
$validator = Validator::make($inputs, [
|
||||
'date' => 'required|date_format:Y/m/d',
|
||||
'time' => 'required|date_format:H:i',
|
||||
'date' => 'required_without:is_realtime|date_format:Y/m/d',
|
||||
'time' => 'required_without:is_realtime|date_format:H:i',
|
||||
'note' => 'nullable|string|max:500',
|
||||
'link' => 'nullable|url|max:2000',
|
||||
'tags' => 'nullable|string',
|
||||
])->after(function ($validator) use ($request, $inputs) {
|
||||
// 日時の重複チェック
|
||||
if (!$validator->errors()->hasAny(['date', 'time'])) {
|
||||
$dt = $inputs['date'] . ' ' . $inputs['time'];
|
||||
if (isset($inputs['date']) && isset($inputs['time'])) {
|
||||
$dt = Carbon::createFromFormat('Y/m/d H:i', $inputs['date'] . ' ' . $inputs['time']);
|
||||
} else {
|
||||
$dt = now();
|
||||
}
|
||||
$dt = $dt->startOfMinute();
|
||||
if (Ejaculation::where(['user_id' => Auth::id(), 'ejaculated_date' => $dt])->count()) {
|
||||
$validator->errors()->add('datetime', '既にこの日時にチェックインしているため、登録できません。');
|
||||
}
|
||||
@@ -59,18 +67,27 @@ class EjaculationController extends Controller
|
||||
});
|
||||
|
||||
if ($validator->fails()) {
|
||||
return redirect()->route('checkin')->withErrors($validator)->withInput();
|
||||
return redirect()->route('checkin')
|
||||
->withErrors($validator)
|
||||
->withInput(array_merge(['is_realtime' => false], $request->input()));
|
||||
}
|
||||
|
||||
$ejaculation = DB::transaction(function () use ($request, $inputs) {
|
||||
if (isset($inputs['date']) && isset($inputs['time'])) {
|
||||
$ejaculatedDate = Carbon::createFromFormat('Y/m/d H:i', $inputs['date'] . ' ' . $inputs['time']);
|
||||
} else {
|
||||
$ejaculatedDate = now();
|
||||
}
|
||||
$ejaculatedDate = $ejaculatedDate->startOfMinute();
|
||||
$ejaculation = Ejaculation::create([
|
||||
'user_id' => Auth::id(),
|
||||
'ejaculated_date' => Carbon::createFromFormat('Y/m/d H:i', $inputs['date'] . ' ' . $inputs['time']),
|
||||
'ejaculated_date' => $ejaculatedDate,
|
||||
'note' => $inputs['note'] ?? '',
|
||||
'link' => $inputs['link'] ?? '',
|
||||
'source' => Ejaculation::SOURCE_WEB,
|
||||
'is_private' => $request->has('is_private') ?? false,
|
||||
'is_too_sensitive' => $request->has('is_too_sensitive') ?? false
|
||||
'is_too_sensitive' => $request->has('is_too_sensitive') ?? false,
|
||||
'discard_elapsed_time' => $request->has('discard_elapsed_time') ?? false,
|
||||
]);
|
||||
|
||||
$tagIds = [];
|
||||
@@ -104,21 +121,7 @@ class EjaculationController extends Controller
|
||||
->firstOrFail();
|
||||
$user = User::findOrFail($ejaculation->user_id);
|
||||
|
||||
// 1つ前のチェックインからの経過時間を求める
|
||||
$previousEjaculation = Ejaculation::select('ejaculated_date')
|
||||
->where('user_id', $ejaculation->user_id)
|
||||
->where('ejaculated_date', '<', $ejaculation->ejaculated_date)
|
||||
->orderByDesc('ejaculated_date')
|
||||
->first();
|
||||
if (!empty($previousEjaculation)) {
|
||||
$ejaculatedSpan = $ejaculation->ejaculated_date
|
||||
->diff($previousEjaculation->ejaculated_date)
|
||||
->format('%a日 %h時間 %i分');
|
||||
} else {
|
||||
$ejaculatedSpan = null;
|
||||
}
|
||||
|
||||
return view('ejaculation.show')->with(compact('user', 'ejaculation', 'ejaculatedSpan'));
|
||||
return view('ejaculation.show')->with(compact('user', 'ejaculation'));
|
||||
}
|
||||
|
||||
public function edit(Request $request, $id)
|
||||
@@ -138,6 +141,7 @@ class EjaculationController extends Controller
|
||||
|
||||
$errors = $request->session()->get('errors');
|
||||
$initialState = [
|
||||
'mode' => 'update',
|
||||
'fields' => [
|
||||
'date' => old('date') ?? $ejaculation->ejaculated_date->format('Y/m/d'),
|
||||
'time' => old('time') ?? $ejaculation->ejaculated_date->format('H:i'),
|
||||
@@ -145,7 +149,8 @@ class EjaculationController extends Controller
|
||||
'tags' => $tags,
|
||||
'note' => old('note') ?? $ejaculation->note,
|
||||
'is_private' => is_bool(old('is_private')) ? old('is_private') : $ejaculation->is_private,
|
||||
'is_too_sensitive' => is_bool(old('is_too_sensitive')) ? old('is_too_sensitive') : $ejaculation->is_too_sensitive
|
||||
'is_too_sensitive' => is_bool(old('is_too_sensitive')) ? old('is_too_sensitive') : $ejaculation->is_too_sensitive,
|
||||
'discard_elapsed_time' => is_bool(old('discard_elapsed_time')) ? old('discard_elapsed_time') : $ejaculation->discard_elapsed_time,
|
||||
],
|
||||
'errors' => isset($errors) ? $errors->getMessages() : null
|
||||
];
|
||||
@@ -187,7 +192,8 @@ class EjaculationController extends Controller
|
||||
'note' => $inputs['note'] ?? '',
|
||||
'link' => $inputs['link'] ?? '',
|
||||
'is_private' => $request->has('is_private') ?? false,
|
||||
'is_too_sensitive' => $request->has('is_too_sensitive') ?? false
|
||||
'is_too_sensitive' => $request->has('is_too_sensitive') ?? false,
|
||||
'discard_elapsed_time' => $request->has('discard_elapsed_time') ?? false,
|
||||
])->save();
|
||||
|
||||
$tagIds = [];
|
||||
|
@@ -28,17 +28,19 @@ class UserController extends Controller
|
||||
// チェックインの取得
|
||||
$query = Ejaculation::select(DB::raw(
|
||||
<<<'SQL'
|
||||
id,
|
||||
ejaculations.id,
|
||||
ejaculated_date,
|
||||
note,
|
||||
is_private,
|
||||
is_too_sensitive,
|
||||
link,
|
||||
source,
|
||||
to_char(lead(ejaculated_date, 1, NULL) OVER (ORDER BY ejaculated_date DESC), 'YYYY/MM/DD HH24:MI') AS before_date,
|
||||
to_char(ejaculated_date - (lead(ejaculated_date, 1, NULL) OVER (ORDER BY ejaculated_date DESC)), 'FMDDD日 FMHH24時間 FMMI分') AS ejaculated_span
|
||||
discard_elapsed_time,
|
||||
to_char(before_dates.before_date, 'YYYY/MM/DD HH24:MI') AS before_date,
|
||||
to_char(ejaculated_date - before_dates.before_date, 'FMDDD日 FMHH24時間 FMMI分') AS ejaculated_span
|
||||
SQL
|
||||
))
|
||||
->joinSub($this->queryBeforeEjaculatedDates(), 'before_dates', 'before_dates.id', '=', 'ejaculations.id')
|
||||
->where('user_id', $user->id);
|
||||
if (!Auth::check() || $user->id !== Auth::id()) {
|
||||
$query = $query->where('is_private', false);
|
||||
@@ -161,17 +163,19 @@ SQL
|
||||
// チェックインの取得
|
||||
$query = Ejaculation::select(DB::raw(
|
||||
<<<'SQL'
|
||||
id,
|
||||
ejaculations.id,
|
||||
ejaculated_date,
|
||||
note,
|
||||
is_private,
|
||||
is_too_sensitive,
|
||||
link,
|
||||
source,
|
||||
to_char(lead(ejaculated_date, 1, NULL) OVER (ORDER BY ejaculated_date DESC), 'YYYY/MM/DD HH24:MI') AS before_date,
|
||||
to_char(ejaculated_date - (lead(ejaculated_date, 1, NULL) OVER (ORDER BY ejaculated_date DESC)), 'FMDDD日 FMHH24時間 FMMI分') AS ejaculated_span
|
||||
discard_elapsed_time,
|
||||
to_char(before_dates.before_date, 'YYYY/MM/DD HH24:MI') AS before_date,
|
||||
to_char(ejaculated_date - before_dates.before_date, 'FMDDD日 FMHH24時間 FMMI分') AS ejaculated_span
|
||||
SQL
|
||||
))
|
||||
->joinSub($this->queryBeforeEjaculatedDates(), 'before_dates', 'before_dates.id', '=', 'ejaculations.id')
|
||||
->where('user_id', $user->id)
|
||||
->where('link', '<>', '');
|
||||
if (!Auth::check() || $user->id !== Auth::id()) {
|
||||
@@ -303,4 +307,14 @@ SQL
|
||||
->groupBy(DB::raw("to_char(ejaculated_date, 'YYYY/MM/DD')"))
|
||||
->orderBy(DB::raw("to_char(ejaculated_date, 'YYYY/MM/DD')"));
|
||||
}
|
||||
|
||||
private function queryBeforeEjaculatedDates()
|
||||
{
|
||||
return DB::table('ejaculations')->selectRaw(
|
||||
<<<'SQL'
|
||||
id,
|
||||
(select ejaculated_date from ejaculations e2 where e2.ejaculated_date < ejaculations.ejaculated_date and e2.user_id = ejaculations.user_id order by e2.ejaculated_date desc limit 1) AS before_date
|
||||
SQL
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@@ -19,6 +19,7 @@ class ProfileStatsComposer
|
||||
if (!$view->offsetExists('user')) {
|
||||
throw new \LogicException('View data "user" was not exist.');
|
||||
}
|
||||
/** @var \App\User $user */
|
||||
$user = $view->offsetGet('user');
|
||||
|
||||
// 現在のオナ禁セッションの経過時間
|
||||
@@ -35,35 +36,44 @@ class ProfileStatsComposer
|
||||
}
|
||||
|
||||
// 概況欄のデータ取得
|
||||
$average = DB::select(<<<'SQL'
|
||||
$average = 0;
|
||||
$divisor = 0;
|
||||
$averageSources = DB::select(<<<'SQL'
|
||||
SELECT
|
||||
avg(span) AS average
|
||||
extract(epoch from ejaculated_date - lead(ejaculated_date, 1, NULL) OVER (ORDER BY ejaculated_date DESC)) AS span,
|
||||
discard_elapsed_time
|
||||
FROM
|
||||
(
|
||||
SELECT
|
||||
extract(epoch from ejaculated_date - lead(ejaculated_date, 1, NULL) OVER (ORDER BY ejaculated_date DESC)) AS span
|
||||
FROM
|
||||
ejaculations
|
||||
WHERE
|
||||
user_id = :user_id
|
||||
ORDER BY
|
||||
ejaculated_date DESC
|
||||
LIMIT
|
||||
30
|
||||
) AS temp
|
||||
ejaculations
|
||||
WHERE
|
||||
user_id = :user_id
|
||||
ORDER BY
|
||||
ejaculated_date DESC
|
||||
LIMIT
|
||||
30
|
||||
SQL
|
||||
, ['user_id' => $user->id]);
|
||||
foreach ($averageSources as $item) {
|
||||
// 経過時間記録対象外のレコードがあったら、それより古いデータは平均の計算に加えない
|
||||
if ($item->discard_elapsed_time) {
|
||||
break;
|
||||
}
|
||||
$average += $item->span;
|
||||
$divisor++;
|
||||
}
|
||||
if ($divisor > 0) {
|
||||
$average /= $divisor;
|
||||
}
|
||||
|
||||
$summary = DB::select(<<<'SQL'
|
||||
SELECT
|
||||
max(span) AS longest,
|
||||
min(span) AS shortest,
|
||||
sum(span) AS total_times,
|
||||
count(*) AS total_checkins
|
||||
sum(span) AS total_times
|
||||
FROM
|
||||
(
|
||||
SELECT
|
||||
extract(epoch from ejaculated_date - lead(ejaculated_date, 1, NULL) OVER (ORDER BY ejaculated_date DESC)) AS span
|
||||
extract(epoch from ejaculated_date - lead(ejaculated_date, 1, NULL) OVER (ORDER BY ejaculated_date DESC)) AS span,
|
||||
discard_elapsed_time
|
||||
FROM
|
||||
ejaculations
|
||||
WHERE
|
||||
@@ -71,9 +81,13 @@ FROM
|
||||
ORDER BY
|
||||
ejaculated_date DESC
|
||||
) AS temp
|
||||
WHERE
|
||||
discard_elapsed_time = FALSE
|
||||
SQL
|
||||
, ['user_id' => $user->id]);
|
||||
|
||||
$view->with(compact('latestEjaculation', 'currentSession', 'average', 'summary'));
|
||||
$total = $user->ejaculations()->count();
|
||||
|
||||
$view->with(compact('latestEjaculation', 'currentSession', 'average', 'summary', 'total'));
|
||||
}
|
||||
}
|
||||
|
@@ -4,6 +4,7 @@ namespace App\MetadataResolver;
|
||||
|
||||
use Carbon\Carbon;
|
||||
use GuzzleHttp\Client;
|
||||
use Symfony\Component\DomCrawler\Crawler;
|
||||
|
||||
class CienResolver extends MetadataResolver
|
||||
{
|
||||
@@ -25,20 +26,27 @@ class CienResolver extends MetadataResolver
|
||||
public function resolve(string $url): Metadata
|
||||
{
|
||||
$res = $this->client->get($url);
|
||||
$metadata = $this->ogpResolver->parse((string) $res->getBody());
|
||||
$html = (string) $res->getBody();
|
||||
$metadata = $this->ogpResolver->parse($html);
|
||||
$crawler = new Crawler($html);
|
||||
|
||||
// 画像URLのJWTから有効期限を拾う
|
||||
// OGPのデフォルトはバナーなので、投稿に使える画像があればそれを使う
|
||||
$selector = 'img[data-actual*="image-web"]';
|
||||
if ($crawler->filter($selector)->count() !== 0) {
|
||||
$metadata->image = $crawler->filter($selector)->attr('data-actual');
|
||||
}
|
||||
|
||||
// JWTがついていれば画像URLのJWTから有効期限を拾う
|
||||
parse_str(parse_url($metadata->image, PHP_URL_QUERY), $params);
|
||||
if (empty($params['jwt'])) {
|
||||
throw new \RuntimeException('Parameter "jwt" not found. Image=' . $metadata->image . ' Source=' . $url);
|
||||
}
|
||||
$parts = explode('.', $params['jwt']);
|
||||
if (count($parts) !== 3) {
|
||||
throw new \RuntimeException('Invalid jwt. Image=' . $metadata->image . ' Source=' . $url);
|
||||
}
|
||||
$payload = json_decode(base64_decode(str_replace(['-', '_'], ['+', '/'], $parts[1])), true);
|
||||
if (isset($params['jwt'])) {
|
||||
$parts = explode('.', $params['jwt']);
|
||||
if (count($parts) !== 3) {
|
||||
throw new \RuntimeException('Invalid jwt. Image=' . $metadata->image . ' Source=' . $url);
|
||||
}
|
||||
$payload = json_decode(base64_decode(str_replace(['-', '_'], ['+', '/'], $parts[1])), true);
|
||||
|
||||
$metadata->expires_at = Carbon::createFromTimestamp($payload['exp']);
|
||||
$metadata->expires_at = Carbon::createFromTimestamp($payload['exp']);
|
||||
}
|
||||
|
||||
return $metadata;
|
||||
}
|
||||
|
978
composer.lock
generated
978
composer.lock
generated
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,32 @@
|
||||
<?php
|
||||
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
|
||||
class AddDiscardElapsedTimeToEjaculations extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function up()
|
||||
{
|
||||
Schema::table('ejaculations', function (Blueprint $table) {
|
||||
$table->boolean('discard_elapsed_time')->default(false);
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::table('ejaculations', function (Blueprint $table) {
|
||||
$table->dropColumn('discard_elapsed_time');
|
||||
});
|
||||
}
|
||||
}
|
@@ -4,7 +4,7 @@ info:
|
||||
description: |
|
||||
夜のライフログサービス Tissue の公開API仕様です。
|
||||
全てのAPIのURLは `https://shikorism.net/api` から始まります。
|
||||
version: 0.1.0
|
||||
version: 0.1.1
|
||||
servers:
|
||||
- url: 'https://shikorism.net/api'
|
||||
paths:
|
||||
@@ -51,6 +51,10 @@ paths:
|
||||
type: boolean
|
||||
default: false
|
||||
description: チェックイン対象のオカズをより過激なオカズとして設定
|
||||
discard_elapsed_time:
|
||||
type: boolean
|
||||
default: false
|
||||
description: 前回チェックインからの経過時間を記録しない
|
||||
examples:
|
||||
simple:
|
||||
description: 何も指定しなければ、現在時刻で公開チェックインをおこないます。
|
||||
|
@@ -10,7 +10,8 @@
|
||||
"production": "cross-env NODE_ENV=production node_modules/webpack/bin/webpack.js --progress --hide-modules --config=node_modules/laravel-mix/setup/webpack.config.js",
|
||||
"eslint": "eslint --ext .js,.ts,.tsx resources/",
|
||||
"stylelint": "stylelint resources/assets/sass/**/*",
|
||||
"doc": "redoc-cli bundle -o public/apidoc.html openapi.yaml"
|
||||
"doc": "redoc-cli bundle -o public/apidoc.html openapi.yaml",
|
||||
"heroku-postbuild": "npm run production && npm run doc"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/bootstrap": "^4.5.0",
|
||||
|
@@ -1,5 +1,6 @@
|
||||
import React, { useState } from 'react';
|
||||
import React, { useState, useEffect } from 'react';
|
||||
import classNames from 'classnames';
|
||||
import { format } from 'date-fns';
|
||||
import { CheckBox } from './CheckBox';
|
||||
import { FieldError, StandaloneFieldError } from './FieldError';
|
||||
import { TagInput } from './TagInput';
|
||||
@@ -10,18 +11,43 @@ type CheckinFormProps = {
|
||||
};
|
||||
|
||||
export const CheckinForm: React.FC<CheckinFormProps> = ({ initialState }) => {
|
||||
const mode = initialState.mode;
|
||||
const [date, setDate] = useState<string>(initialState.fields.date || '');
|
||||
const [time, setTime] = useState<string>(initialState.fields.time || '');
|
||||
const [tags, setTags] = useState<string[]>(initialState.fields.tags || []);
|
||||
const [link, setLink] = useState<string>(initialState.fields.link || '');
|
||||
const [linkForPreview, setLinkForPreview] = useState(link);
|
||||
const [note, setNote] = useState<string>(initialState.fields.note || '');
|
||||
const [isRealtime, setRealtime] = useState<boolean>(mode === 'create' && initialState.fields.is_realtime);
|
||||
const [isPrivate, setPrivate] = useState<boolean>(!!initialState.fields.is_private);
|
||||
const [isTooSensitive, setTooSensitive] = useState<boolean>(!!initialState.fields.is_too_sensitive);
|
||||
const [discardElapsedTime, setDiscardElapsedTime] = useState<boolean>(!!initialState.fields.discard_elapsed_time);
|
||||
useEffect(() => {
|
||||
if (mode === 'create' && isRealtime) {
|
||||
const id = setInterval(() => {
|
||||
const now = new Date();
|
||||
setDate(format(now, 'yyyy/MM/dd'));
|
||||
setTime(format(now, 'HH:mm'));
|
||||
}, 500);
|
||||
return () => clearInterval(id);
|
||||
}
|
||||
}, [mode, isRealtime]);
|
||||
|
||||
return (
|
||||
<>
|
||||
<div className="form-row">
|
||||
{mode === 'create' && (
|
||||
<div className="col-sm-12 mb-2">
|
||||
<CheckBox
|
||||
id="isRealtime"
|
||||
name="is_realtime"
|
||||
checked={isRealtime}
|
||||
onChange={(v) => setRealtime(v)}
|
||||
>
|
||||
現在時刻でチェックイン
|
||||
</CheckBox>
|
||||
</div>
|
||||
)}
|
||||
<div className="form-group col-sm-6">
|
||||
<label htmlFor="date">
|
||||
<span className="oi oi-calendar" /> 日付
|
||||
@@ -38,6 +64,7 @@ export const CheckinForm: React.FC<CheckinFormProps> = ({ initialState }) => {
|
||||
required
|
||||
value={date}
|
||||
onChange={(e) => setDate(e.target.value)}
|
||||
disabled={isRealtime}
|
||||
/>
|
||||
<FieldError errors={initialState.errors?.date} />
|
||||
</div>
|
||||
@@ -57,6 +84,7 @@ export const CheckinForm: React.FC<CheckinFormProps> = ({ initialState }) => {
|
||||
required
|
||||
value={time}
|
||||
onChange={(e) => setTime(e.target.value)}
|
||||
disabled={isRealtime}
|
||||
/>
|
||||
<FieldError errors={initialState.errors?.time} />
|
||||
</div>
|
||||
@@ -137,6 +165,23 @@ export const CheckinForm: React.FC<CheckinFormProps> = ({ initialState }) => {
|
||||
>
|
||||
<span className="oi oi-warning" /> チェックイン対象のオカズをより過激なオカズとして設定する
|
||||
</CheckBox>
|
||||
<CheckBox
|
||||
id="discardElapsedTime"
|
||||
name="discard_elapsed_time"
|
||||
className="mb-3"
|
||||
checked={discardElapsedTime}
|
||||
onChange={(v) => setDiscardElapsedTime(v)}
|
||||
>
|
||||
<span className="oi oi-timer" /> 前回チェックインからの経過時間を記録しない
|
||||
<br />
|
||||
<small className="form-text text-muted">
|
||||
長期間お使いにならなかった場合など、経過時間に意味が無い時のリセット用オプションです。
|
||||
<ul className="pl-3">
|
||||
<li>最長・最短記録の計算から除外されます。</li>
|
||||
<li>平均記録の起点がこのチェックインになります。</li>
|
||||
</ul>
|
||||
</small>
|
||||
</CheckBox>
|
||||
</div>
|
||||
</div>
|
||||
<div className="text-center">
|
||||
|
@@ -23,8 +23,7 @@ export const TagInput: React.FC<TagInputProps> = ({ id, name, values, isInvalid,
|
||||
case 'Enter':
|
||||
case ' ':
|
||||
if ((event as any).isComposing !== true) {
|
||||
onChange && onChange(values.concat(buffer.trim().replace(/\s+/g, '_')));
|
||||
setBuffer('');
|
||||
commitBuffer();
|
||||
}
|
||||
event.preventDefault();
|
||||
break;
|
||||
@@ -32,8 +31,7 @@ export const TagInput: React.FC<TagInputProps> = ({ id, name, values, isInvalid,
|
||||
// 実際にテキストボックスに入力されている文字を見に行く (フォールバック処理)
|
||||
const nativeEvent = event.nativeEvent;
|
||||
if (nativeEvent.srcElement && (nativeEvent.srcElement as HTMLInputElement).value.slice(-1) == ' ') {
|
||||
onChange && onChange(values.concat(buffer.trim().replace(/\s+/g, '_')));
|
||||
setBuffer('');
|
||||
commitBuffer();
|
||||
event.preventDefault();
|
||||
}
|
||||
break;
|
||||
@@ -45,6 +43,13 @@ export const TagInput: React.FC<TagInputProps> = ({ id, name, values, isInvalid,
|
||||
}
|
||||
};
|
||||
|
||||
const commitBuffer = () => {
|
||||
const newTag = buffer.trim().replace(/\s+/g, '_');
|
||||
if (newTag.length === 0) return;
|
||||
onChange && onChange(values.concat(newTag));
|
||||
setBuffer('');
|
||||
};
|
||||
|
||||
return (
|
||||
<div className={containerClass} onClick={() => inputRef.current?.focus()}>
|
||||
<input name={name} type="hidden" value={values.join(' ')} />
|
||||
@@ -66,6 +71,7 @@ export const TagInput: React.FC<TagInputProps> = ({ id, name, values, isInvalid,
|
||||
className="tis-tag-input-field"
|
||||
value={buffer}
|
||||
onChange={(e) => setBuffer(e.target.value)}
|
||||
onBlur={commitBuffer}
|
||||
onKeyDown={onKeyDown}
|
||||
/>
|
||||
</li>
|
||||
|
24
resources/assets/sass/_underline-tabs.scss
vendored
Normal file
24
resources/assets/sass/_underline-tabs.scss
vendored
Normal file
@@ -0,0 +1,24 @@
|
||||
.tis-nav-underline-tabs {
|
||||
margin-bottom: -1px;
|
||||
|
||||
.nav-link {
|
||||
padding: 0.5rem 1.25rem;
|
||||
color: $secondary;
|
||||
border-bottom: 2px solid transparent;
|
||||
transition: border-bottom-color .12s ease-in;
|
||||
|
||||
@include media-breakpoint-up(lg) {
|
||||
padding: 1rem 1.25rem;
|
||||
}
|
||||
|
||||
&.active {
|
||||
color: $primary;
|
||||
border-bottom-color: $primary;
|
||||
}
|
||||
|
||||
&:not(.active):hover {
|
||||
border-bottom-color: transparentize($secondary, 0.3);
|
||||
transition: border-bottom-color .4s ease-out;
|
||||
}
|
||||
}
|
||||
}
|
9
resources/assets/sass/app.scss
vendored
9
resources/assets/sass/app.scss
vendored
@@ -15,6 +15,15 @@ $primary: #e53fb1;
|
||||
@import "components/link-card";
|
||||
@import "components/tag-input";
|
||||
@import "components/metadata-preview";
|
||||
@import "components/profile-mini";
|
||||
|
||||
// Tag
|
||||
@import "tag/index";
|
||||
|
||||
// Underline tabs
|
||||
@import "underline-tabs";
|
||||
|
||||
// Status containerの後続要素との余白調整
|
||||
.tis-status-container + .mt-n1 {
|
||||
margin-top: 0 !important;
|
||||
}
|
||||
|
11
resources/assets/sass/components/_profile-mini.scss
vendored
Normal file
11
resources/assets/sass/components/_profile-mini.scss
vendored
Normal file
@@ -0,0 +1,11 @@
|
||||
.tis-profile-mini {
|
||||
&-display-name {
|
||||
font-size: 1.2rem;
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
&-name {
|
||||
margin-top: 0.125rem;
|
||||
font-size: 0.8rem;
|
||||
}
|
||||
}
|
17
resources/views/components/header-dropdown-menu.blade.php
Normal file
17
resources/views/components/header-dropdown-menu.blade.php
Normal file
@@ -0,0 +1,17 @@
|
||||
<a href="{{ route('user.profile', ['name' => Auth::user()->name]) }}" class="dropdown-item">
|
||||
<strong>{{ Auth::user()->display_name }}</strong>
|
||||
<p class="mb-0 text-muted">
|
||||
<span>@{{ Auth::user()->name }}</span>
|
||||
</p>
|
||||
</a>
|
||||
<div class="dropdown-divider"></div>
|
||||
<a href="{{ route('user.profile', ['name' => Auth::user()->name]) }}" class="dropdown-item">プロフィール</a>
|
||||
<a href="{{ route('user.stats', ['name' => Auth::user()->name]) }}" class="dropdown-item">グラフ</a>
|
||||
<a href="{{ route('user.okazu', ['name' => Auth::user()->name]) }}" class="dropdown-item">オカズ</a>
|
||||
<a href="{{ route('user.likes', ['name' => Auth::user()->name]) }}" class="dropdown-item">いいね</a>
|
||||
<div class="dropdown-divider"></div>
|
||||
<a href="{{ route('setting') }}" class="dropdown-item">設定</a>
|
||||
@can ('admin')
|
||||
<a href="{{ route('admin.dashboard') }}" class="dropdown-item">管理</a>
|
||||
@endcan
|
||||
<a href="{{ route('logout') }}" class="dropdown-item" onclick="event.preventDefault(); document.getElementById('logout-form').submit();">ログアウト</a>
|
20
resources/views/components/profile-bio.blade.php
Normal file
20
resources/views/components/profile-bio.blade.php
Normal file
@@ -0,0 +1,20 @@
|
||||
@if (!empty($user->bio) || !empty($user->url))
|
||||
<div class="card mb-4">
|
||||
<div class="card-body">
|
||||
{{-- Bio --}}
|
||||
@if (!empty($user->bio))
|
||||
<p class="card-text mb-0">
|
||||
{!! Formatter::linkify(nl2br(e($user->bio))) !!}
|
||||
</p>
|
||||
@endif
|
||||
|
||||
{{-- URL --}}
|
||||
@if (!empty($user->url))
|
||||
<p class="card-text d-flex mt-3">
|
||||
<span class="oi oi-link-intact mr-1 mt-1"></span>
|
||||
<a href="{{ $user->url }}" rel="me nofollow noopener" target="_blank" class="text-truncate">{{ preg_replace('~\Ahttps?://~', '', $user->url) }}</a>
|
||||
</p>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
@endif
|
@@ -1,14 +1,14 @@
|
||||
<div class="d-flex flex-row align-items-end {{ $class ?? '' }}">
|
||||
<img src="{{ $user->getProfileImageUrl(48) }}" srcset="{{ Formatter::profileImageSrcSet($user, 48) }}" class="rounded mr-2">
|
||||
<div class="d-flex flex-column overflow-hidden">
|
||||
<h5 class="card-title text-truncate">
|
||||
<div class="tis-profile-mini-display-name text-truncate">
|
||||
<a class="text-dark" href="{{ route('user.profile', ['name' => $user->name]) }}">{{ $user->display_name }}</a>
|
||||
</h5>
|
||||
<h6 class="card-subtitle">
|
||||
</div>
|
||||
<div class="tis-profile-mini-name">
|
||||
<a class="text-muted" href="{{ route('user.profile', ['name' => $user->name]) }}">@{{ $user->name }}</a>
|
||||
@if ($user->is_protected)
|
||||
<span class="oi oi-lock-locked text-muted"></span>
|
||||
@endif
|
||||
</h6>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
@@ -8,8 +8,8 @@
|
||||
@endif
|
||||
|
||||
<h6 class="font-weight-bold"><span class="oi oi-graph"></span> 概況</h6>
|
||||
<p class="card-text mb-0">平均記録: {{ Formatter::formatInterval($average[0]->average) }}</p>
|
||||
<p class="card-text mb-0">平均記録: {{ Formatter::formatInterval($average) }}</p>
|
||||
<p class="card-text mb-0">最長記録: {{ Formatter::formatInterval($summary[0]->longest) }}</p>
|
||||
<p class="card-text mb-0">最短記録: {{ Formatter::formatInterval($summary[0]->shortest) }}</p>
|
||||
<p class="card-text mb-0">合計時間: {{ Formatter::formatInterval($summary[0]->total_times) }}</p>
|
||||
<p class="card-text">通算回数: {{ number_format($summary[0]->total_checkins) }}回</p>
|
||||
<p class="card-text">通算回数: {{ number_format($total) }}回</p>
|
||||
|
@@ -5,7 +5,7 @@
|
||||
<a class="text-dark" href="{{ route('user.profile', ['name' => $user->name]) }}">{{ $user->display_name }}</a>
|
||||
</h4>
|
||||
<h6 class="card-subtitle">
|
||||
<a class="text-muted" href="{{ route('user.profile', ['name' => $user->name]) }}">@{{ $user->name }}</a>
|
||||
<a class="text-muted font-weight-normal" href="{{ route('user.profile', ['name' => $user->name]) }}">@{{ $user->name }}</a>
|
||||
@if ($user->is_protected)
|
||||
<span class="oi oi-lock-locked text-muted"></span>
|
||||
@endif
|
||||
|
@@ -31,7 +31,7 @@
|
||||
<div class="card-body">
|
||||
<!-- span -->
|
||||
<div>
|
||||
<h5>{{ $ejaculatedSpan ?? '精通' }} <small class="text-muted">{{ $ejaculation->before_date }}{{ !empty($ejaculation->before_date) ? ' ~ ' : '' }}{{ $ejaculation->ejaculated_date->format('Y/m/d H:i') }}</small></h5>
|
||||
<h5>{{ $ejaculation->ejaculatedSpan() }} <small class="text-muted">{{ !empty($ejaculation->before_date) && !$ejaculation->discard_elapsed_time ? $ejaculation->before_date . ' ~ ' : '' }}{{ $ejaculation->ejaculated_date->format('Y/m/d H:i') }}</small></h5>
|
||||
</div>
|
||||
<!-- tags -->
|
||||
@if ($ejaculation->is_private || $ejaculation->source !== 'web' || $ejaculation->tags->isNotEmpty())
|
||||
|
@@ -43,21 +43,7 @@
|
||||
<img src="{{ Auth::user()->getProfileImageUrl(30) }}" srcset="{{ Formatter::profileImageSrcSet(Auth::user(), 30) }}" width="30" height="30" class="rounded d-inline-block align-top">
|
||||
</a>
|
||||
<div class="dropdown-menu dropdown-menu-right position-absolute" aria-labelledby="navbarDropdownMenuLink" id="navbarAccountDropdownSp">
|
||||
<a href="{{ route('user.profile', ['name' => Auth::user()->name]) }}" class="dropdown-item text-truncate">
|
||||
<strong>{{ Auth::user()->display_name }}</strong>
|
||||
<p class="mb-0 text-muted">
|
||||
<span>@{{ Auth::user()->name }}</span>
|
||||
</p>
|
||||
</a>
|
||||
<div class="dropdown-divider"></div>
|
||||
<a href="{{ route('user.profile', ['name' => Auth::user()->name]) }}" class="dropdown-item">プロフィール</a>
|
||||
<a href="{{ route('user.likes', ['name' => Auth::user()->name]) }}" class="dropdown-item">いいね</a>
|
||||
<div class="dropdown-divider"></div>
|
||||
<a href="{{ route('setting') }}" class="dropdown-item">設定</a>
|
||||
@can ('admin')
|
||||
<a href="{{ route('admin.dashboard') }}" class="dropdown-item">管理</a>
|
||||
@endcan
|
||||
<a href="{{ route('logout') }}" class="dropdown-item" onclick="event.preventDefault(); document.getElementById('logout-form').submit();">ログアウト</a>
|
||||
@include('components.header-dropdown-menu')
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@@ -73,14 +59,8 @@
|
||||
<li class="nav-item {{ stripos(Route::currentRouteName(), 'home') === 0 ? 'active' : ''}}">
|
||||
<a class="nav-link" href="{{ route('home') }}">ホーム</a>
|
||||
</li>
|
||||
<li class="nav-item {{ stripos(Route::currentRouteName(), 'user.profile') === 0 ? 'active' : ''}}">
|
||||
<a class="nav-link" href="{{ route('user.profile', ['name' => Auth::user()->name]) }}">タイムライン</a>
|
||||
</li>
|
||||
<li class="nav-item {{ stripos(Route::currentRouteName(), 'user.stats') === 0 ? 'active' : ''}}">
|
||||
<a class="nav-link" href="{{ route('user.stats', ['name' => Auth::user()->name]) }}">グラフ</a>
|
||||
</li>
|
||||
<li class="nav-item {{ stripos(Route::currentRouteName(), 'user.okazu') === 0 ? 'active' : ''}}">
|
||||
<a class="nav-link" href="{{ route('user.okazu', ['name' => Auth::user()->name]) }}">オカズ</a>
|
||||
<li class="nav-item {{ stripos(Route::currentRouteName(), 'timeline.public') === 0 ? 'active' : ''}}">
|
||||
<a class="nav-link" href="{{ route('timeline.public') }}">お惣菜</a>
|
||||
</li>
|
||||
<li class="nav-item {{ stripos(Route::currentRouteName(), 'tag') === 0 ? 'active' : ''}}">
|
||||
<a class="nav-link" href="{{ route('tag') }}">タグ一覧</a>
|
||||
@@ -106,21 +86,7 @@
|
||||
<img src="{{ Auth::user()->getProfileImageUrl(30) }}" srcset="{{ Formatter::profileImageSrcSet(Auth::user(), 30) }}" width="30" height="30" class="rounded d-inline-block align-top">
|
||||
</a>
|
||||
<div class="dropdown-menu dropdown-menu-right" aria-labelledby="navbarDropdownMenuLink">
|
||||
<a href="{{ route('user.profile', ['name' => Auth::user()->name]) }}" class="dropdown-item">
|
||||
<strong>{{ Auth::user()->display_name }}</strong>
|
||||
<p class="mb-0 text-muted">
|
||||
<span>@{{ Auth::user()->name }}</span>
|
||||
</p>
|
||||
</a>
|
||||
<div class="dropdown-divider"></div>
|
||||
<a href="{{ route('user.profile', ['name' => Auth::user()->name]) }}" class="dropdown-item">プロフィール</a>
|
||||
<a href="{{ route('user.likes', ['name' => Auth::user()->name]) }}" class="dropdown-item">いいね</a>
|
||||
<div class="dropdown-divider"></div>
|
||||
<a href="{{ route('setting') }}" class="dropdown-item">設定</a>
|
||||
@can ('admin')
|
||||
<a href="{{ route('admin.dashboard') }}" class="dropdown-item">管理</a>
|
||||
@endcan
|
||||
<a href="{{ route('logout') }}" class="dropdown-item" onclick="event.preventDefault(); document.getElementById('logout-form').submit();">ログアウト</a>
|
||||
@include('components.header-dropdown-menu')
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
@@ -132,15 +98,7 @@
|
||||
<a class="btn btn-{{ stripos(Route::currentRouteName(), 'home') === 0 ? 'primary' : 'outline-secondary'}}" href="{{ route('home') }}" role="button">ホーム</a>
|
||||
</div>
|
||||
<div class="col">
|
||||
<a class="btn btn-{{ stripos(Route::currentRouteName(), 'user.profile') === 0 ? 'primary' : 'outline-secondary'}}" href="{{ route('user.profile', ['name' => Auth::user()->name]) }}" role="button">タイムライン</a>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row mt-2">
|
||||
<div class="col">
|
||||
<a class="btn btn-{{ stripos(Route::currentRouteName(), 'user.stats') === 0 ? 'primary' : 'outline-secondary'}}" href="{{ route('user.stats', ['name' => Auth::user()->name]) }}" role="button">グラフ</a>
|
||||
</div>
|
||||
<div class="col">
|
||||
<a class="btn btn-{{ stripos(Route::currentRouteName(), 'user.okazu') === 0 ? 'primary' : 'outline-secondary'}}" href="{{ route('user.okazu', ['name' => Auth::user()->name]) }}" role="button">オカズ</a>
|
||||
<a class="btn btn-{{ stripos(Route::currentRouteName(), 'timeline.public') === 0 ? 'primary' : 'outline-secondary'}}" href="{{ route('timeline.public') }}" role="button">お惣菜</a>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row mt-2">
|
||||
@@ -204,7 +162,7 @@
|
||||
</div>
|
||||
</nav>
|
||||
@if (session('status'))
|
||||
<div class="container">
|
||||
<div class="container tis-status-container">
|
||||
<div id="status" class="alert alert-success alert-dismissible fade show" role="alert">
|
||||
{{ session('status') }}
|
||||
<button type="button" class="close" data-dismiss="alert" aria-label="Close">
|
||||
|
@@ -1,46 +1,45 @@
|
||||
@extends('layouts.base')
|
||||
|
||||
@section('content')
|
||||
<div class="container">
|
||||
<div class="row">
|
||||
<div class="col-lg-4">
|
||||
@if (Route::currentRouteName() === 'user.profile')
|
||||
@component('components.profile', ['user' => $user])
|
||||
<div class="container-fluid border-bottom mb-4 mt-n1 mt-lg-n4 px-0">
|
||||
<div class="container">
|
||||
<div class="row align-items-center">
|
||||
<div class="col-lg-4">
|
||||
@component('components.profile-mini', ['user' => $user])
|
||||
@endcomponent
|
||||
@else
|
||||
<div class="card mb-4">
|
||||
<div class="card-body">
|
||||
@component('components.profile-mini', ['user' => $user])
|
||||
@endcomponent
|
||||
</div>
|
||||
</div>
|
||||
@endif
|
||||
@section('sidebar')
|
||||
@show
|
||||
</div>
|
||||
<div class="col-lg-8">
|
||||
<ul class="nav nav-tabs">
|
||||
<li class="nav-item">
|
||||
<a class="nav-link {{ Route::currentRouteName() === 'user.profile' ? 'active' : '' }}" href="{{ route('user.profile', ['name' => $user->name]) }}">タイムライン</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link {{ stripos(Route::currentRouteName(), 'user.stats') === 0 ? 'active' : '' }}" href="{{ route('user.stats', ['name' => $user->name]) }}">グラフ</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link {{ Route::currentRouteName() === 'user.okazu' ? 'active' : '' }}" href="{{ route('user.okazu', ['name' => $user->name]) }}">オカズ</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link {{ Route::currentRouteName() === 'user.likes' ? 'active' : '' }}" href="{{ route('user.likes', ['name' => $user->name]) }}">いいね
|
||||
@if ($user->isMe() || !($user->is_protected || $user->private_likes))
|
||||
<span class="badge badge-primary">{{ $user->likes()->count() }}</span>
|
||||
@endif
|
||||
</a>
|
||||
</li>
|
||||
</ul>
|
||||
<div class="tab-content">
|
||||
@yield('tab-content')
|
||||
</div>
|
||||
<div class="col-lg-8 mt-3 mt-lg-2 px-0 px-md-2">
|
||||
<ul class="nav tis-nav-underline-tabs flex-nowrap overflow-auto">
|
||||
<li class="nav-item flex-shrink-0">
|
||||
<a class="nav-link {{ Route::currentRouteName() === 'user.profile' ? 'active' : '' }}" href="{{ route('user.profile', ['name' => $user->name]) }}">タイムライン</a>
|
||||
</li>
|
||||
<li class="nav-item flex-shrink-0">
|
||||
<a class="nav-link {{ stripos(Route::currentRouteName(), 'user.stats') === 0 ? 'active' : '' }}" href="{{ route('user.stats', ['name' => $user->name]) }}">グラフ</a>
|
||||
</li>
|
||||
<li class="nav-item flex-shrink-0">
|
||||
<a class="nav-link {{ Route::currentRouteName() === 'user.okazu' ? 'active' : '' }}" href="{{ route('user.okazu', ['name' => $user->name]) }}">オカズ</a>
|
||||
</li>
|
||||
<li class="nav-item flex-shrink-0">
|
||||
<a class="nav-link {{ Route::currentRouteName() === 'user.likes' ? 'active' : '' }}" href="{{ route('user.likes', ['name' => $user->name]) }}">いいね
|
||||
@if ($user->isMe() || !($user->is_protected || $user->private_likes))
|
||||
<span class="badge {{ Route::currentRouteName() === 'user.likes' ? 'badge-primary' : 'badge-secondary' }}">{{ $user->likes()->count() }}</span>
|
||||
@endif
|
||||
</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="container">
|
||||
<div class="row">
|
||||
<div class="col-lg-4">
|
||||
@section('sidebar')
|
||||
@show
|
||||
</div>
|
||||
<div class="col-lg-8">
|
||||
@yield('tab-content')
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@endsection
|
||||
|
@@ -11,6 +11,16 @@
|
||||
@section('sidebar')
|
||||
{{-- TODO: タイムラインとオカズのテンプレを分けたら条件外す --}}
|
||||
@if (Route::currentRouteName() === 'user.profile')
|
||||
@component('components.profile-bio', ['user' => $user])
|
||||
@endcomponent
|
||||
@if (!$user->is_protected || $user->isMe())
|
||||
<div class="card mb-4">
|
||||
<div class="card-body">
|
||||
@component('components.profile-stats', ['user' => $user])
|
||||
@endcomponent
|
||||
</div>
|
||||
</div>
|
||||
@endif
|
||||
@if (!empty($tags) && (!$user->is_protected || $user->isMe()))
|
||||
<div class="card mb-4">
|
||||
<div class="card-header">
|
||||
@@ -48,7 +58,7 @@
|
||||
<li class="list-group-item border-bottom-only pt-3 pb-3 text-break">
|
||||
<!-- span -->
|
||||
<div>
|
||||
<h5>{{ $ejaculation->ejaculated_span ?? '精通' }} <a href="{{ route('checkin.show', ['id' => $ejaculation->id]) }}" class="text-muted"><small>{{ $ejaculation->before_date }}{{ !empty($ejaculation->before_date) ? ' ~ ' : '' }}{{ $ejaculation->ejaculated_date->format('Y/m/d H:i') }}</small></a></h5>
|
||||
<h5>{{ $ejaculation->ejaculatedSpan() }} <a href="{{ route('checkin.show', ['id' => $ejaculation->id]) }}" class="text-muted"><small>{{ !empty($ejaculation->before_date) && !$ejaculation->discard_elapsed_time ? $ejaculation->before_date . ' ~ ' : '' }}{{ $ejaculation->ejaculated_date->format('Y/m/d H:i') }}</small></a></h5>
|
||||
</div>
|
||||
<!-- tags -->
|
||||
@if ($ejaculation->is_private || $ejaculation->source !== 'web' || $ejaculation->tags->isNotEmpty())
|
||||
|
@@ -25,24 +25,29 @@ class CienResolverTest extends TestCase
|
||||
$this->createResolver(CienResolver::class, $responseText);
|
||||
|
||||
$metadata = $this->resolver->resolve('https://ci-en.dlsite.com/creator/2462/article/87502');
|
||||
$this->assertSame('進捗とボツ立ち絵 - ねんない5 - Ci-en(シエン)', $metadata->title);
|
||||
$this->assertSame('今日のサムネイルはストアページに掲載する予定のキャラクター紹介画像です。 ドットでない解像度の高いイラストは時間も体力も精神力もかかるので、こういうのを行うタスクを開発終盤に残さないでよかったと本気……', $metadata->description);
|
||||
$this->assertStringStartsWith('https://media.ci-en.jp/private/attachment/creator/00002462/a7afd3b02a6d1caa6afe6a3bf5550fb6a42aefba686f17a0a2f63c97fd6867ab/image-800.jpg?jwt=', $metadata->image);
|
||||
$this->assertSame('進捗とボツ立ち絵 - ねんない5 - Ci-en', $metadata->title);
|
||||
$this->assertSame('ドット製2D ACTを製作しています。' . PHP_EOL . '恐ろしい存在に襲われる絶望感や、被虐的な官能がテーマです。', $metadata->description);
|
||||
$this->assertStringStartsWith('https://media.ci-en.jp/private/attachment/creator/00002462/a7afd3b02a6d1caa6afe6a3bf5550fb6a42aefba686f17a0a2f63c97fd6867ab/image-web.jpg?jwt=', $metadata->image);
|
||||
if ($this->shouldUseMock()) {
|
||||
$this->assertSame('https://media.ci-en.jp/private/attachment/creator/00002462/a7afd3b02a6d1caa6afe6a3bf5550fb6a42aefba686f17a0a2f63c97fd6867ab/image-800.jpg?jwt=eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJrZXkiOiJqd3RhdXRoX3NlY18yMDIwT2N0IiwiaXNzIjoiaHR0cHM6XC9cL2NpLWVuLmRsc2l0ZS5jb21cLyIsInN1YiI6IjAwMDAwMDAwMDAwIiwiYXVkIjoiYTdhZmQzYjAyYTZkMWNhYTZhZmU2YTNiZjU1NTBmYjZhNDJhZWZiYTY4NmYxN2EwYTJmNjNjOTdmZDY4NjdhYiIsImV4cCI6MTYwMjk5NTIyMX0.bXUG2T6nXl4hdvsvt1wkIMvbbBdsKk-xbwB6SaxARZA', $metadata->image);
|
||||
$this->assertSame(1602995221, $metadata->expires_at->timestamp);
|
||||
$this->assertSame('https://media.ci-en.jp/private/attachment/creator/00002462/a7afd3b02a6d1caa6afe6a3bf5550fb6a42aefba686f17a0a2f63c97fd6867ab/image-web.jpg?jwt=eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJrZXkiOiJqd3RhdXRoX3NlY18yMDIwT2N0IiwiaXNzIjoiaHR0cHM6XC9cL2NpLWVuLmRsc2l0ZS5jb21cLyIsInN1YiI6IjAwMDAwMDAwMDAwIiwiYXVkIjoiYTdhZmQzYjAyYTZkMWNhYTZhZmU2YTNiZjU1NTBmYjZhNDJhZWZiYTY4NmYxN2EwYTJmNjNjOTdmZDY4NjdhYiIsImV4cCI6MTYwNzA2NzMyOX0.-462_WtZ6AUOxrfndBE-0_oWHKwesP9mMMn6K2oYQJM', $metadata->image);
|
||||
$this->assertSame(1607067329, $metadata->expires_at->timestamp);
|
||||
$this->assertSame('https://ci-en.dlsite.com/creator/2462/article/87502', (string) $this->handler->getLastRequest()->getUri());
|
||||
}
|
||||
}
|
||||
|
||||
public function testWithNoTimestamp()
|
||||
public function testWithNoPostImage()
|
||||
{
|
||||
$responseText = $this->fetchSnapshot(__DIR__ . '/../../fixture/Cien/testWithNoTimestamp.html');
|
||||
$responseText = $this->fetchSnapshot(__DIR__ . '/../../fixture/Cien/testWithNoPostImage.html');
|
||||
|
||||
$this->createResolver(CienResolver::class, $responseText);
|
||||
|
||||
$this->expectException(\RuntimeException::class);
|
||||
$this->expectExceptionMessage('Parameter "jwt" not found. Image=https://ci-en.dlsite.com/assets/img/common/logo_Ci-en_R18.svg Source=https://ci-en.dlsite.com/');
|
||||
|
||||
$this->resolver->resolve('https://ci-en.dlsite.com/');
|
||||
$metadata = $this->resolver->resolve('https://ci-en.dlsite.com/creator/148/article/401866');
|
||||
$this->assertSame('近況報告 - 薄稀 - Ci-en', $metadata->title);
|
||||
$this->assertSame('サキュバスをはじめ、M向けの魔物娘をよく描くエロ絵描きです(´ω`)', $metadata->description);
|
||||
$this->assertSame('https://media.ci-en.jp/public/cover/creator/00000148/9153a13f78591bc2c9efae1021a26f9b90d24d3b30a0b3e699d0050f09dab6df/image-990-c.jpg', $metadata->image);
|
||||
if ($this->shouldUseMock()) {
|
||||
$this->assertNull($metadata->expires_at);
|
||||
$this->assertSame('https://ci-en.dlsite.com/creator/148/article/401866', (string) $this->handler->getLastRequest()->getUri());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
1622
tests/fixture/Cien/test.html
vendored
1622
tests/fixture/Cien/test.html
vendored
File diff suppressed because one or more lines are too long
1102
tests/fixture/Cien/testWithNoPostImage.html
vendored
Normal file
1102
tests/fixture/Cien/testWithNoPostImage.html
vendored
Normal file
File diff suppressed because one or more lines are too long
602
tests/fixture/Cien/testWithNoTimestamp.html
vendored
602
tests/fixture/Cien/testWithNoTimestamp.html
vendored
@@ -1,602 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="ja">
|
||||
|
||||
<head>
|
||||
|
||||
<meta name="google-site-verification" content="4UtUmaro4aJIR94PZdv-GoliXlDvtUVFL03-9CTh68s" />
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" id="viewport" content="width=device-width, user-scalable=no, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, viewport-fit=cover">
|
||||
<meta name="csrf-token" content="1UAeVYZqG3XqR5XwRi0MXYJn3zIf51glrKZKY2gp">
|
||||
<meta name="app-auth-check" content="0">
|
||||
|
||||
<meta property="og:title" content="Ci-en">
|
||||
<meta property="og:type" content="website">
|
||||
<meta property="og:url" content="http://ci-en.dlsite.com">
|
||||
<meta property="og:image" content="https://ci-en.dlsite.com/assets/img/common/logo_Ci-en_R18.svg">
|
||||
<meta property="og:site_name" content="Ci-en">
|
||||
<meta property="og:description" content="好きの気持ちは、カタチで伝えよう。">
|
||||
<meta name="twitter:card" content="summary_large_image">
|
||||
<meta name="twitter:title" content="Ci-en">
|
||||
<meta name="twitter:description" content="好きの気持ちは、カタチで伝えよう。">
|
||||
<meta name="twitter:image:src" content="https://ci-en.dlsite.com/assets/img/common/logo_Ci-en_R18.svg">
|
||||
|
||||
<meta name="description" content="好きの気持ちは、カタチで伝えよう。">
|
||||
<meta name="keyword" content="Ci-en">
|
||||
<meta name="sentry-public-dsn" content="7319f62f11fe408b932254c5fe87eb64@sentry.io/301968">
|
||||
<meta name="sentry-release" content="fd2635a6350eda85e4dbec5559f0172e7f8086df">
|
||||
<meta name="app-locale" content="ja">
|
||||
<title>好きの気持ちは、カタチで伝えよう。 - Ci-en</title>
|
||||
<link media="all" type="text/css" rel="stylesheet" href="https://ci-en.dlsite.com/assets/css/app.css?1567667013">
|
||||
<link rel="icon" href="/favicon.ico">
|
||||
<link rel="stylesheet" href="https://www.dlsite.com/assets/share/css/universal/universal.css">
|
||||
|
||||
|
||||
|
||||
<script>(function(w,d,s,l,i){w[l]=w[l]||[];w[l].push({'gtm.start':
|
||||
new Date().getTime(),event:'gtm.js'});var f=d.getElementsByTagName(s)[0],
|
||||
j=d.createElement(s),dl=l!='dataLayer'?'&l='+l:'';j.async=true;j.src=
|
||||
'https://www.googletagmanager.com/gtm.js?id='+i+dl;f.parentNode.insertBefore(j,f);
|
||||
})(window,document,'script','dataLayer','GTM-NNPHW5Z');</script>
|
||||
|
||||
<script async src="https://www.googletagmanager.com/gtag/js?id=UA-109913020-1"></script>
|
||||
<script>
|
||||
window.dataLayer = window.dataLayer || [];
|
||||
function gtag(){
|
||||
dataLayer.push(arguments);
|
||||
}
|
||||
gtag('js', new Date());
|
||||
|
||||
gtag('config', 'UA-109913020-1', {
|
||||
'send_page_view': false,
|
||||
'custom_map': {
|
||||
'dimension1':'logined',
|
||||
},
|
||||
});
|
||||
gtag('set', 'linker', {
|
||||
'accept_incoming': true,
|
||||
'domains': ['ci-en.net','ci-en.dlsite.com']
|
||||
});
|
||||
gtag('event', 'page_view', {
|
||||
'logined': '',
|
||||
'has_creator': '0',
|
||||
});
|
||||
|
||||
|
||||
|
||||
|
||||
</script>
|
||||
</head>
|
||||
|
||||
<body class="global-layout p-topPage ">
|
||||
<!-- グローバルヘッダー -->
|
||||
<div class="l-eisysGroupHeader type-cien">
|
||||
<vue-global-header
|
||||
account-settings-url="https://login.dlsite.com/user/self?redirect_uri=https%3A%2F%2Fci-en.dlsite.com%2Flogout&lang=ja"
|
||||
is-adult="1"
|
||||
user-id=""
|
||||
creator-id=""
|
||||
></vue-global-header>
|
||||
</div>
|
||||
<header class="global-layout-item type-header">
|
||||
<div class="header-inner">
|
||||
|
||||
<div class="cien-logo type-r18">
|
||||
<a href="/">Ci-en</a>
|
||||
</div>
|
||||
|
||||
<form method="GET" action="https://ci-en.dlsite.com/search" accept-charset="UTF-8" class="hd-searchBox">
|
||||
<input type="text" class="hd-searchInput" name="keyword" placeholder="クリエイターを検索">
|
||||
<input type="submit" class="hd-searchButton" value="">
|
||||
</form>
|
||||
|
||||
|
||||
<div class="nav-drawer type-menu">
|
||||
<input id="nav-inputMenu" type="checkbox" class="nav-unshown">
|
||||
<label id="nav-open" for="nav-inputMenu">
|
||||
<span></span>
|
||||
</label>
|
||||
<label class="nav-unshown icon-navClose" id="nav-close" for="nav-inputMenu"><span></span></label>
|
||||
<div class="nav-content type-left">
|
||||
|
||||
|
||||
<div class="navEntry">
|
||||
<p class="text">DLsiteアカウントをお持ちの方はログインできます。</p>
|
||||
<div class="btnBox">
|
||||
<a href="https://ci-en.dlsite.com/login" class="btn type-basic">ログイン</a>
|
||||
<a href="https://ci-en.dlsite.com/login" class="btn type-important">新規登録</a>
|
||||
</div>
|
||||
<p class="notice">株式会社エイシスが運営しているサービスをDLsiteアカウント一つでご利用いただけます。</p>
|
||||
</div>
|
||||
<ul class="nav-submenuList">
|
||||
<li class="nav-submenuList-item"><a href="https://ci-en.dlsite.com/about/supporter">Ci-enとは?</a></li>
|
||||
<li class="nav-submenuList-item"><a href="https://ci-en.dlsite.com/about/creator">クリエイター登録</a></li>
|
||||
<li class="nav-submenuList-item"><a href="https://ci-en.dlsite.com/about/faq">よくある質問</a></li>
|
||||
</ul>
|
||||
|
||||
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
|
||||
<div class="globalNav-wrap">
|
||||
<ul class="globalNav is-guest">
|
||||
|
||||
<li class="globalNav-item type-bell">
|
||||
|
||||
<a href="https://ci-en.dlsite.com/mypage/activity">
|
||||
<span class="globalNav-icon">通知</span>
|
||||
</a>
|
||||
</li>
|
||||
|
||||
<li class="globalNav-item type-searchBox">
|
||||
<form method="GET" action="https://ci-en.dlsite.com/search" accept-charset="UTF-8" class="hd-search">
|
||||
<input type="submit" class="hd-searchButton" value="">
|
||||
<input type="text" class="hd-searchInput" name="keyword" placeholder="クリエイターを検索">
|
||||
</form>
|
||||
</li>
|
||||
|
||||
|
||||
<li class="globalNav-item type-search ">
|
||||
<a href="https://ci-en.dlsite.com/search/top">
|
||||
<span class="globalNav-icon"></span>
|
||||
</a>
|
||||
</li>
|
||||
|
||||
<li class="globalNav-item type-signup">
|
||||
<a href="https://ci-en.dlsite.com/login">Ci-enをはじめる</a>
|
||||
</li>
|
||||
|
||||
<li class="globalNav-item type-mypage">
|
||||
<a href="https://ci-en.dlsite.com/mypage">
|
||||
<span class="globalNav-icon">マイページ</span>
|
||||
</a>
|
||||
</li>
|
||||
|
||||
|
||||
<li class="globalNav-item type-help">
|
||||
<a href="https://ci-en.dlsite.com/about/faq">
|
||||
<span class="globalNav-icon">ヘルプ</span>
|
||||
</a>
|
||||
</li>
|
||||
|
||||
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
</header>
|
||||
<section class="global-layout-item type-contentsNav">
|
||||
</section>
|
||||
<section id="detail" class="global-layout-item type-contents">
|
||||
<section class="grid-container inner-layout">
|
||||
<div class="topHeroArea" onload="console.log('loaded');">
|
||||
<h1 class="topCatchcopy">
|
||||
<div class="catchcopy-item type-first"></div>
|
||||
<div class="catchcopy-item type-last"></div>
|
||||
</h1>
|
||||
<div id="top-heroarea-mainimg" class="topHeroArea-mainImg">
|
||||
<div class="mainImg-item item-twinkleStar"></div>
|
||||
<div class="mainImg-item item-twinkleStar1"></div>
|
||||
<div class="mainImg-item item-twinkleStar2"></div>
|
||||
<div class="mainImg-item item-star"></div>
|
||||
<div class="topHeroArea-gradeFilter"></div>
|
||||
<div class="mainImg-item item-wood"></div>
|
||||
<div class="mainImg-item item-donguri"></div>
|
||||
<div class="mainImg-item item-present"></div>
|
||||
<div class="mainImg-item item-letter"></div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="grid-item grid-main">
|
||||
|
||||
<div class="topIntroArea">
|
||||
<h1 class="topIntroArea-heading"></h1>
|
||||
<div class="topIntroArea-textGroup">
|
||||
<p class="text">新しいものを作るのは、簡単なことではありません。<span>思いを形にするには時間と手間、そして資金が必要です。</span></p>
|
||||
<p class="text">Ci-enで好きなクリエイターを支援すれば、<span>その収益を創作活動に活かすことができるようになります。</span></p>
|
||||
<p class="text">クリエイターも支援者も、誰もが創作を楽しめる世界に参加してみませんか?</p>
|
||||
</div>
|
||||
<div class="topIntroArea-btn">
|
||||
<a href="https://login.dlsite.com/register?redirect_uri=https%3A%2F%2Fci-en.dlsite.com&lang=ja" class="btn type-important-confirm">Ci-enをはじめる</a>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<div class="topAboutCienArea">
|
||||
<div class="topAboutCienArea-main"></div>
|
||||
<div class="topAboutCienArea-btn">
|
||||
<a href="https://ci-en.dlsite.com/about/supporter" class="btn type-confirm">もっと知りたい方はこちら</a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div id="follow" class="topLetsFollowArea">
|
||||
<div class="topLetsFollowArea-heading"></div>
|
||||
<div class="topLetsFollowArea-body">
|
||||
|
||||
<div class="topShowcase type-popularCreator">
|
||||
<div class="topShowcase-heading">
|
||||
<a href="//ci-en.net#follow" class="btn type-topRatingChange">全年齢に切替</a>
|
||||
</div>
|
||||
|
||||
<div class="topShowcase-body">
|
||||
<div class="mod-creatorCard at-topPage">
|
||||
<div class="creatorCard-header">
|
||||
<img src="https://media.ci-en.jp/public/cover/creator/00000208/6742fc1b379a180e4485cdeff9a086d535725683ca882155b400bc65ab13ed3e/image-990-c.jpg" alt="">
|
||||
</div>
|
||||
<div class="creatorCard-body">
|
||||
<dt class="creatorCard-thumb">
|
||||
<div class="accountIcon type-cerator size-m">
|
||||
<img src="https://media.ci-en.jp/public/icon/creator/00000208/6f0dac0278bbb547e97b0deddd2aad22043d6b9ce8cde868b99e543d7dc1ec9f/image-200-c.jpg" alt="">
|
||||
</div>
|
||||
</dt>
|
||||
<dd class="creatorCard-name">ONEONE1</dd>
|
||||
<dd class="creatorCard-tag">
|
||||
<ul class="tagList type-creator">
|
||||
<li class="tagList-item type-creator">
|
||||
<a class="item-tag type-activityGenre" href="/search?categoryId=9">ゲーム</a>
|
||||
</li>
|
||||
</ul>
|
||||
</dd>
|
||||
</div>
|
||||
<a href="https://ci-en.dlsite.com/creator/208" class="creatorCard-link"></a>
|
||||
</div>
|
||||
<div class="mod-creatorCard at-topPage">
|
||||
<div class="creatorCard-header">
|
||||
<img src="https://media.ci-en.jp/public/cover/creator/00001145/4f39516e4f22c76b45443b5567789419d8d0ea985958cd26adea88cf79c95fd3/image-990-c.jpg" alt="">
|
||||
</div>
|
||||
<div class="creatorCard-body">
|
||||
<dt class="creatorCard-thumb">
|
||||
<div class="accountIcon type-cerator size-m">
|
||||
<img src="https://media.ci-en.jp/public/icon/creator/00001145/5c18c657f97e23ea73a700784f55c2e34b1871e532b45e32118ee57a6c2cb677/image-200-c.jpg" alt="">
|
||||
</div>
|
||||
</dt>
|
||||
<dd class="creatorCard-name">同人サークルGyu!</dd>
|
||||
<dd class="creatorCard-tag">
|
||||
<ul class="tagList type-creator">
|
||||
<li class="tagList-item type-creator">
|
||||
<a class="item-tag type-activityGenre" href="/search?categoryId=9">ゲーム</a>
|
||||
</li>
|
||||
</ul>
|
||||
</dd>
|
||||
</div>
|
||||
<a href="https://ci-en.dlsite.com/creator/1145" class="creatorCard-link"></a>
|
||||
</div>
|
||||
<div class="mod-creatorCard at-topPage">
|
||||
<div class="creatorCard-header">
|
||||
<img src="https://media.ci-en.jp/public/cover/creator/00000057/a8c0cf4f84fc374e9ba5891ee2a158a69067eee0d3601a66e1e00489df4df25d/image-990-c.jpg" alt="">
|
||||
</div>
|
||||
<div class="creatorCard-body">
|
||||
<dt class="creatorCard-thumb">
|
||||
<div class="accountIcon type-cerator size-m">
|
||||
<img src="https://media.ci-en.jp/public/icon/creator/00000057/72fbd8b3e2124f88de11866d21a23c6e4ff375e62dba50c517f537655ff2e981/image-200-c.jpg" alt="">
|
||||
</div>
|
||||
</dt>
|
||||
<dd class="creatorCard-name">クリメニア</dd>
|
||||
<dd class="creatorCard-tag">
|
||||
<ul class="tagList type-creator">
|
||||
<li class="tagList-item type-creator">
|
||||
<a class="item-tag type-activityGenre" href="/search?categoryId=9">ゲーム</a>
|
||||
</li>
|
||||
</ul>
|
||||
</dd>
|
||||
</div>
|
||||
<a href="https://ci-en.dlsite.com/creator/57" class="creatorCard-link"></a>
|
||||
</div>
|
||||
<div class="mod-creatorCard at-topPage">
|
||||
<div class="creatorCard-header">
|
||||
<img src="https://media.ci-en.jp/public/cover/creator/00001321/5e327eb84b4ce6a36be637729b000ba74a9b27f35273f08a30b86e464ee1e25e/image-990-c.jpg" alt="">
|
||||
</div>
|
||||
<div class="creatorCard-body">
|
||||
<dt class="creatorCard-thumb">
|
||||
<div class="accountIcon type-cerator size-m">
|
||||
<img src="https://media.ci-en.jp/public/icon/creator/00001321/60557adcbb149f7494c6aed36f3d44373896a971b997af3e4e02a650f70f5cbe/image-200-c.jpg" alt="">
|
||||
</div>
|
||||
</dt>
|
||||
<dd class="creatorCard-name">Hypnotic Yanh</dd>
|
||||
<dd class="creatorCard-tag">
|
||||
<ul class="tagList type-creator">
|
||||
<li class="tagList-item type-creator">
|
||||
<a class="item-tag type-activityGenre" href="/search?categoryId=8">音声作品</a>
|
||||
</li>
|
||||
</ul>
|
||||
</dd>
|
||||
</div>
|
||||
<a href="https://ci-en.dlsite.com/creator/1321" class="creatorCard-link"></a>
|
||||
</div>
|
||||
<div class="mod-creatorCard at-topPage">
|
||||
<div class="creatorCard-header">
|
||||
<img src="https://media.ci-en.jp/public/cover/creator/00000391/f0134aaa1e2174efabc30e024c973024f34064e0f6ab6738477564c34170ae3b/image-990-c.jpg" alt="">
|
||||
</div>
|
||||
<div class="creatorCard-body">
|
||||
<dt class="creatorCard-thumb">
|
||||
<div class="accountIcon type-cerator size-m">
|
||||
<img src="https://media.ci-en.jp/public/icon/creator/00000391/c98d97cf4d4af1c6aad452150693a06a63e6f4323e21ad0848e83f910a949b80/image-200-c.jpg" alt="">
|
||||
</div>
|
||||
</dt>
|
||||
<dd class="creatorCard-name">シロクマの嫁(伊ヶ崎綾香)</dd>
|
||||
<dd class="creatorCard-tag">
|
||||
<ul class="tagList type-creator">
|
||||
<li class="tagList-item type-creator">
|
||||
<a class="item-tag type-activityGenre" href="/search?categoryId=8">音声作品</a>
|
||||
</li>
|
||||
</ul>
|
||||
</dd>
|
||||
</div>
|
||||
<a href="https://ci-en.dlsite.com/creator/391" class="creatorCard-link"></a>
|
||||
</div>
|
||||
<div class="mod-creatorCard at-topPage">
|
||||
<div class="creatorCard-header">
|
||||
<img src="https://media.ci-en.jp/public/cover/creator/00001058/14ccafc478078692f53a62c0e2ea722d55dd018945d44c31e55bdcc237ee9944/image-990-c.jpg" alt="">
|
||||
</div>
|
||||
<div class="creatorCard-body">
|
||||
<dt class="creatorCard-thumb">
|
||||
<div class="accountIcon type-cerator size-m">
|
||||
<img src="https://media.ci-en.jp/public/icon/creator/00001058/3ac1827236a6fce3d5d7d9142dd4e77e3b732b63db18af81e5c74818572d7b10/image-200-c.jpg" alt="">
|
||||
</div>
|
||||
</dt>
|
||||
<dd class="creatorCard-name">鉱油/73号坑道</dd>
|
||||
<dd class="creatorCard-tag">
|
||||
<ul class="tagList type-creator">
|
||||
<li class="tagList-item type-creator">
|
||||
<a class="item-tag type-activityGenre" href="/search?categoryId=9">ゲーム</a>
|
||||
</li>
|
||||
</ul>
|
||||
</dd>
|
||||
</div>
|
||||
<a href="https://ci-en.dlsite.com/creator/1058" class="creatorCard-link"></a>
|
||||
</div>
|
||||
<div class="mod-creatorCard at-topPage">
|
||||
<div class="creatorCard-header">
|
||||
<img src="https://media.ci-en.jp/public/cover/creator/00000190/0ebc04b8de8d6e42f6c5bf020936bff79bdfa29ab71f1ea2eff547f42fd9caa7/image-990-c.jpg" alt="">
|
||||
</div>
|
||||
<div class="creatorCard-body">
|
||||
<dt class="creatorCard-thumb">
|
||||
<div class="accountIcon type-cerator size-m">
|
||||
<img src="https://media.ci-en.jp/public/icon/creator/00000190/e5e01272dac25575a00b651adf8d04524d91a87ff534bc4391dbabea404e6a49/image-200-c.jpg" alt="">
|
||||
</div>
|
||||
</dt>
|
||||
<dd class="creatorCard-name">ぽいずん</dd>
|
||||
<dd class="creatorCard-tag">
|
||||
<ul class="tagList type-creator">
|
||||
<li class="tagList-item type-creator">
|
||||
<a class="item-tag type-activityGenre" href="/search?categoryId=9">ゲーム</a>
|
||||
</li>
|
||||
</ul>
|
||||
</dd>
|
||||
</div>
|
||||
<a href="https://ci-en.dlsite.com/creator/190" class="creatorCard-link"></a>
|
||||
</div>
|
||||
<div class="mod-creatorCard at-topPage">
|
||||
<div class="creatorCard-header">
|
||||
<img src="https://media.ci-en.jp/public/cover/creator/00002004/b568c5bcc1108db1276c32b550140f5d539a92c589f3bd8fc16163fba56eb50a/image-990-c.jpg" alt="">
|
||||
</div>
|
||||
<div class="creatorCard-body">
|
||||
<dt class="creatorCard-thumb">
|
||||
<div class="accountIcon type-cerator size-m">
|
||||
<img src="https://media.ci-en.jp/public/icon/creator/00002004/aab5ff3de14c0361715b4a16cc3cc6961cac72b84762d514e6fc38c40dda81e6/image-200-c.jpg" alt="">
|
||||
</div>
|
||||
</dt>
|
||||
<dd class="creatorCard-name">あいすシチュー</dd>
|
||||
<dd class="creatorCard-tag">
|
||||
<ul class="tagList type-creator">
|
||||
<li class="tagList-item type-creator">
|
||||
<a class="item-tag type-activityGenre" href="/search?categoryId=9">ゲーム</a>
|
||||
</li>
|
||||
</ul>
|
||||
</dd>
|
||||
</div>
|
||||
<a href="https://ci-en.dlsite.com/creator/2004" class="creatorCard-link"></a>
|
||||
</div>
|
||||
<div class="mod-creatorCard at-topPage">
|
||||
<div class="creatorCard-header">
|
||||
<img src="https://media.ci-en.jp/public/cover/creator/00001191/b0ca242c5095531d78a95f3bc4e15a5b642b33c808f91af1cf95723dee7a4543/image-990-c.jpg" alt="">
|
||||
</div>
|
||||
<div class="creatorCard-body">
|
||||
<dt class="creatorCard-thumb">
|
||||
<div class="accountIcon type-cerator size-m">
|
||||
<img src="https://media.ci-en.jp/public/icon/creator/00001191/950a61d5e3648e8c01c31a9a3ee127c8cb8e5e015379feb45d409f61acf9cf5a/image-200-c.jpg" alt="">
|
||||
</div>
|
||||
</dt>
|
||||
<dd class="creatorCard-name">みこにそみ</dd>
|
||||
<dd class="creatorCard-tag">
|
||||
<ul class="tagList type-creator">
|
||||
<li class="tagList-item type-creator">
|
||||
<a class="item-tag type-activityGenre" href="/search?categoryId=9">ゲーム</a>
|
||||
</li>
|
||||
</ul>
|
||||
</dd>
|
||||
</div>
|
||||
<a href="https://ci-en.dlsite.com/creator/1191" class="creatorCard-link"></a>
|
||||
</div>
|
||||
<div class="mod-creatorCard at-topPage">
|
||||
<div class="creatorCard-header">
|
||||
<img src="https://media.ci-en.jp/public/cover/creator/00000944/8b3b9c5cc1024bf0b532b9a0db168db7600a77ed6fbeaf15eb4c56656659666d/image-990-c.jpg" alt="">
|
||||
</div>
|
||||
<div class="creatorCard-body">
|
||||
<dt class="creatorCard-thumb">
|
||||
<div class="accountIcon type-cerator size-m">
|
||||
<img src="https://media.ci-en.jp/public/icon/creator/00000944/9dc7439b9801ac6f0e66e92f8980fb2771cb8ab2f8a05e230c753d0f953ce4e0/image-200-c.jpg" alt="">
|
||||
</div>
|
||||
</dt>
|
||||
<dd class="creatorCard-name">D-LIS-ディーリス</dd>
|
||||
<dd class="creatorCard-tag">
|
||||
<ul class="tagList type-creator">
|
||||
<li class="tagList-item type-creator">
|
||||
<a class="item-tag type-activityGenre" href="/search?categoryId=9">ゲーム</a>
|
||||
</li>
|
||||
</ul>
|
||||
</dd>
|
||||
</div>
|
||||
<a href="https://ci-en.dlsite.com/creator/944" class="creatorCard-link"></a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="topShowcase type-searchByGenre">
|
||||
<div class="topShowcase-heading"></div>
|
||||
<div class="topShowcase-body">
|
||||
<div class="topGenre-item">
|
||||
<a href="/search?categoryId=9" class="topGenre-link">
|
||||
ゲーム
|
||||
|
||||
</a>
|
||||
</div>
|
||||
<div class="topGenre-item">
|
||||
<a href="/search?categoryId=1" class="topGenre-link">
|
||||
イラスト
|
||||
|
||||
</a>
|
||||
</div>
|
||||
<div class="topGenre-item">
|
||||
<a href="/search?categoryId=2" class="topGenre-link">
|
||||
漫画
|
||||
|
||||
</a>
|
||||
</div>
|
||||
<div class="topGenre-item">
|
||||
<a href="/search?categoryId=8" class="topGenre-link">
|
||||
音声作品
|
||||
|
||||
</a>
|
||||
</div>
|
||||
<div class="topGenre-item">
|
||||
<a href="/search?categoryId=3" class="topGenre-link">
|
||||
小説
|
||||
|
||||
</a>
|
||||
</div>
|
||||
<div class="topGenre-item">
|
||||
<a href="/search?categoryId=7" class="topGenre-link">
|
||||
声優・歌い手
|
||||
|
||||
</a>
|
||||
</div>
|
||||
<div class="topGenre-item">
|
||||
<a href="/search?categoryId=12" class="topGenre-link">
|
||||
映像・アニメ
|
||||
|
||||
</a>
|
||||
</div>
|
||||
<div class="topGenre-item">
|
||||
<a href="/search?categoryId=17" class="topGenre-link">
|
||||
その他
|
||||
|
||||
</a>
|
||||
</div>
|
||||
<div class="topGenre-item">
|
||||
<a href="/search?categoryId=10" class="topGenre-link">
|
||||
YouTuber・実況
|
||||
|
||||
</a>
|
||||
</div>
|
||||
<div class="topGenre-item">
|
||||
<a href="/search?categoryId=14" class="topGenre-link">
|
||||
VR
|
||||
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="topRegisterCreatorArea">
|
||||
<div class="topRegisterCreatorArea-body">
|
||||
<div class="topRegisterCreatorArea-main">
|
||||
|
||||
<div class="topRegisterCreatorArea-mainImg"></div>
|
||||
|
||||
<div class="topRegisterCreatorArea-btn">
|
||||
<a href="https://ci-en.dlsite.com/about/creator" class="btn type-important-confirm">クリエイター登録について</a>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="topRegisterArea">
|
||||
<div class="topRegisterArea-body">
|
||||
<div class="topRegisterArea-main">
|
||||
<p class="topRegisterArea-text">DLsiteアカウントをお持ちの方はログインできます。</p>
|
||||
<div class="btnBox">
|
||||
<a href="https://ci-en.dlsite.com/login" class="btn type-confirm">ログイン</a>
|
||||
<a href="https://login.dlsite.com/register?redirect_uri=https%3A%2F%2Fci-en.dlsite.com&lang=ja" class="btn type-important-confirm" target="_blank">新規登録</a>
|
||||
</div>
|
||||
<p class="topRegisterArea-annotation">株式会社エイシスが運営しているサービスをDLsiteアカウント一つでご利用いただけます。</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</section>
|
||||
</section>
|
||||
<footer class="global-layout-item type-footer">
|
||||
<div class="gotoTOPContainer">
|
||||
<a href="#" class="ankerlink">ページトップ</a>
|
||||
</div>
|
||||
|
||||
<div class="globalFooter">
|
||||
<div class="footerContainer innerSpaceFooter">
|
||||
<dl class="footerNav itemNum1">
|
||||
<dt class="footerNav-title">Ci-enについて</dt>
|
||||
<dd class="footerNav-item"><a href="https://ci-en.dlsite.com/about/supporter" class="footerLink">Ci-enとは?</a></dd>
|
||||
<dd class="footerNav-item"><a href="https://ci-en.dlsite.com/about/creator" class="footerLink">クリエイター登録</a></dd>
|
||||
<dd class="footerNav-item"><a href="https://ci-en.dlsite.com/about/faq" class="footerLink">よくある質問(支援者)</a></dd>
|
||||
<dd class="footerNav-item"><a href="https://ci-en.dlsite.com/about/creator-faq" class="footerLink">よくある質問(クリエイター)</a></dd>
|
||||
<dd class="footerNav-item"><a href="https://ci-en.dlsite.com/inquiry" class="footerLink">お問い合わせ</a></dd>
|
||||
<dd class="footerNav-item"><a href="http://info.ci-en.net" target="_blank" class="footerLink">お知らせブログ</a></dd>
|
||||
</dl>
|
||||
|
||||
<dl class="footerNav itemNum2">
|
||||
<dt class="footerNav-title">運営情報</dt>
|
||||
<dd class="footerNav-item"><a href="http://www.eisys.co.jp/company/company-info.html" target="_blank" class="footerLink">会社概要</a></dd>
|
||||
<dd class="footerNav-item"><a href="https://ci-en.dlsite.com/legal/regulation" class="footerLink">利用規約</a></dd>
|
||||
<dd class="footerNav-item"><a href="https://ci-en.dlsite.com/legal/law" class="footerLink">特定商取引法に基づく表示</a></dd>
|
||||
<dd class="footerNav-item"><a href="https://ci-en.dlsite.com/legal/censorship" class="footerLink">コンプライアンスポリシー</a></dd>
|
||||
<dd class="footerNav-item"><a href="https://ci-en.dlsite.com/legal/privacy" class="footerLink">個人情報の取り扱いについて</a></dd>
|
||||
</dl>
|
||||
|
||||
<div class="l-eisysGroupFooter type-cien is-sponly">
|
||||
<div class="eisysGroupFooterInner">
|
||||
<p class="eisysGroupFooterHeading">関連サービス</p>
|
||||
<ul class="eisysGroupFooterService">
|
||||
<li class="eisysGroupFooterService-link type-dlsite">
|
||||
<a href="https://www.dlsite.com/maniax-touch/?utm_campaign=cien&utm_medium=text&utm_content=sp_globalfooter"><span>ダウンロードショップ</span>DLsite</a>
|
||||
</li>
|
||||
<li class="eisysGroupFooterService-link type-nijiyome">
|
||||
<a href="https://www.nijiyome.jp/?en=cien&em=text&et=sp_globalfooter"><span>オンラインゲームサイト</span>にじよめ</a>
|
||||
</li>
|
||||
<li class="eisysGroupFooterService-link type-channel">
|
||||
<a href="https://ch.dlsite.com/?from=sp_globalfooter_cien"><span>二次元コミュニティサイト</span>DLチャンネル</a>
|
||||
</li>
|
||||
<li class="eisysGroupFooterService-link type-chobit">
|
||||
<a href="https://chobit.cc/?from=sp_globalfooter_cien"><span>無料体験版サイト</span>chobit</a>
|
||||
</li>
|
||||
<li class="eisysGroupFooterService-link type-triokini">
|
||||
<a href="https://triokini.com/how_to_use?from=sp_globalfooter_cien"><span>即売会取り置きサイト</span>トリオキニ</a>
|
||||
</li>
|
||||
<li class="eisysGroupFooterService-link type-studio">
|
||||
<a href="https://dlsitestudio.com/?from=sp_globalfooter_cien"><span>音声収録スタジオ</span>DLsiteスタジオ</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="snsArea">
|
||||
<p class="heading">SNS公式アカウント</p>
|
||||
<a href="https://twitter.com/cien_info?lang=ja" class="twitter_link" target="_blink" rel="nofollow noopener"></a>
|
||||
</div>
|
||||
<p class="copyright">© 2018 Ci-en</p>
|
||||
</div>
|
||||
</footer>
|
||||
<script src="https://ci-en.dlsite.com/assets/js/vendor.bundle.js?1568167511"></script>
|
||||
<script src="https://ci-en.dlsite.com/assets/js/app.bundle.js?1568167511"></script>
|
||||
</body>
|
||||
</html>
|
||||
|
35
yarn.lock
35
yarn.lock
@@ -3097,7 +3097,7 @@ debug@2.6.9, debug@^2.2.0, debug@^2.3.3:
|
||||
dependencies:
|
||||
ms "2.0.0"
|
||||
|
||||
debug@^3.0.0, debug@^3.1.0, debug@^3.1.1, debug@^3.2.5:
|
||||
debug@^3.1.0, debug@^3.1.1, debug@^3.2.5:
|
||||
version "3.2.6"
|
||||
resolved "https://registry.yarnpkg.com/debug/-/debug-3.2.6.tgz#e83d17de16d8a7efb7717edbe5fb10135eee629b"
|
||||
integrity sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==
|
||||
@@ -3358,9 +3358,9 @@ domutils@^1.5.1, domutils@^1.7.0:
|
||||
domelementtype "1"
|
||||
|
||||
dot-prop@^4.1.1:
|
||||
version "4.2.0"
|
||||
resolved "https://registry.yarnpkg.com/dot-prop/-/dot-prop-4.2.0.tgz#1f19e0c2e1aa0e32797c49799f2837ac6af69c57"
|
||||
integrity sha512-tUMXrxlExSW6U2EXiiKGSBVdYgtV8qlHL+C10TsW4PURY/ic+eaysnSkwB4kA/mBlCyy/IKDJ+Lc3wbWeaXtuQ==
|
||||
version "4.2.1"
|
||||
resolved "https://registry.yarnpkg.com/dot-prop/-/dot-prop-4.2.1.tgz#45884194a71fc2cda71cbb4bceb3a4dd2f433ba4"
|
||||
integrity sha512-l0p4+mIuJIua0mhxGoh4a+iNL9bmeK5DvnSVQa6T0OhrVmaEa1XScX5Etc673FePCJOArq/4Pa2cLGODUWTPOQ==
|
||||
dependencies:
|
||||
is-obj "^1.0.0"
|
||||
|
||||
@@ -3774,15 +3774,10 @@ etag@~1.8.1:
|
||||
resolved "https://registry.yarnpkg.com/etag/-/etag-1.8.1.tgz#41ae2eeb65efa62268aebfea83ac7d79299b0887"
|
||||
integrity sha1-Qa4u62XvpiJorr/qg6x9eSmbCIc=
|
||||
|
||||
eventemitter3@^4.0.0:
|
||||
version "4.0.0"
|
||||
resolved "https://registry.yarnpkg.com/eventemitter3/-/eventemitter3-4.0.0.tgz#d65176163887ee59f386d64c82610b696a4a74eb"
|
||||
integrity sha512-qerSRB0p+UDEssxTtm6EDKcE7W4OaoisfIMl4CngyEhjpYglocpNg6UEqCvemdGhosAsg4sO2dXJOdyBifPGCg==
|
||||
|
||||
eventemitter3@^4.0.4:
|
||||
version "4.0.4"
|
||||
resolved "https://registry.yarnpkg.com/eventemitter3/-/eventemitter3-4.0.4.tgz#b5463ace635a083d018bdc7c917b4c5f10a85384"
|
||||
integrity sha512-rlaVLnVxtxvoyLsQQFBx53YmXHDxRIzzTLbdfxqi4yocpSjAxXwkU0cScM5JgSKMqEhrZpnvQ2D9gjylR0AimQ==
|
||||
eventemitter3@^4.0.0, eventemitter3@^4.0.4:
|
||||
version "4.0.7"
|
||||
resolved "https://registry.yarnpkg.com/eventemitter3/-/eventemitter3-4.0.7.tgz#2de9b68f6528d5644ef5c59526a1b4a07306169f"
|
||||
integrity sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw==
|
||||
|
||||
events@^3.0.0:
|
||||
version "3.1.0"
|
||||
@@ -4158,11 +4153,9 @@ fn-name@~2.0.1:
|
||||
integrity sha1-UhTXU3pNBqSjAcDMJi/rhBiAAuc=
|
||||
|
||||
follow-redirects@^1.0.0:
|
||||
version "1.9.1"
|
||||
resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.9.1.tgz#26e329669886f8b3baccbaf352067b0253da6c2d"
|
||||
integrity sha512-oUNbrdUjHItyCytZQrHxWQ81ebL4xCFLH10sG0poUMgbKWoBnswpICjUBld3PLJ1lF6cCYVUBG7hAdLro0JNvg==
|
||||
dependencies:
|
||||
debug "^3.0.0"
|
||||
version "1.13.0"
|
||||
resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.13.0.tgz#b42e8d93a2a7eea5ed88633676d6597bc8e384db"
|
||||
integrity sha512-aq6gF1BEKje4a9i9+5jimNFIpq4Q1WiwBToeRK5NvZBd/TRsmW8BsJfOEGkr76TbOyPVD3OVDN910EcUNtRYEA==
|
||||
|
||||
for-in@^1.0.2:
|
||||
version "1.0.2"
|
||||
@@ -4746,9 +4739,9 @@ http-proxy-middleware@0.19.1:
|
||||
micromatch "^3.1.10"
|
||||
|
||||
http-proxy@^1.17.0:
|
||||
version "1.18.0"
|
||||
resolved "https://registry.yarnpkg.com/http-proxy/-/http-proxy-1.18.0.tgz#dbe55f63e75a347db7f3d99974f2692a314a6a3a"
|
||||
integrity sha512-84I2iJM/n1d4Hdgc6y2+qY5mDaz2PUVjlg9znE9byl+q0uC3DeByqBGReQu5tpLK0TAqTIXScRUV+dg7+bUPpQ==
|
||||
version "1.18.1"
|
||||
resolved "https://registry.yarnpkg.com/http-proxy/-/http-proxy-1.18.1.tgz#401541f0534884bbf95260334e72f88ee3976549"
|
||||
integrity sha512-7mz/721AbnJwIVbnaSv1Cz3Am0ZLT/UBwkC92VlxhXv/k/BBQfM2fXElQNC27BVGr0uwUpplYPQM9LnaBMR5NQ==
|
||||
dependencies:
|
||||
eventemitter3 "^4.0.0"
|
||||
follow-redirects "^1.0.0"
|
||||
|
Reference in New Issue
Block a user