精品欧美一区二区三区在线观看 _久久久久国色av免费观看性色_国产精品久久在线观看_亚洲第一综合网站_91精品又粗又猛又爽_小泽玛利亚一区二区免费_91亚洲精品国偷拍自产在线观看 _久久精品视频在线播放_美女精品久久久_欧美日韩国产成人在线

探究 LightHouse 工作流程

開發(fā) 開發(fā)工具
Chrome DevTools 協(xié)議允許使用工具來檢測、檢查、調試和分析 Chromium、Chrome 和其他基于 Blink 的瀏覽器。 在Chrome擴展中,Chrome protocol 利用 chrome.debugger Api 通過 WebSocket[3] 來建立連接。

本文為來自 字節(jié)教育-智能學習-前端團隊 的文章,已授權 ELab 發(fā)布。

智能學習前端團隊 自創(chuàng)立以來,團隊專注于打破大眾對教育的刻板印象,突破固有的教學思維,攻破各類教學屏障。旨在為每一位學生制定最合適的學習方案,予以因材施教,使優(yōu)質教育隨‘觸’可達。

什么是 Lighthouse

Lighthouse analyzes web apps and web pages, collecting modern performance metrics and insights on developer best practices.

圖片

使用方式

  • Chrome 瀏覽器插件。Chrome 插件的形式提供了更加友好的用戶界面,方便讀取報告。
  • Chrome DevTools。該工具集成在最新版本的 Chrome 瀏覽器中,無需安裝即可使用。
  • Lighthouse CLI 命令行工具。方便將 Lighthouse 集成到持續(xù)集成系統(tǒng)中。
  • 代碼中引用。我們也能通過 Node.js 模塊引入 Lighthouse 工具包。

原理結構[1]

圖片

圖片

Gathering

Driver 驅動

通過 Chrome Debugging Protocol 和 Puppeteer[2] (提供無頭瀏覽器環(huán)境模擬頁面操作) /進行交互。

Chrome Debugging Protocol(CDP)

Chrome DevTools 協(xié)議允許使用工具來檢測、檢查、調試和分析 Chromium、Chrome 和其他基于 Blink 的瀏覽器。 在Chrome擴展中,Chrome protocol 利用 chrome.debugger Api 通過 WebSocket[3] 來建立連接。

Instrumentation 分為多個 Domains(DOM, Debugger, Network 等)。每個 Domain 定義了許多它支持的命令和它生成的事件。命令和事件都是固定結構的序列化 JSON 對象。

圖片

CDP Domains,紅色為實驗性

Domain 必須 enable() 后才可以發(fā)出事件。一旦啟用enable,它們將刷新表示狀態(tài)的所有事件。因此,網絡事件僅在 enable() 后才會發(fā)出。所有協(xié)議代理解析 enable() 的回調。比如:

// will NOT work
driver.defaultSession.sendCommand('Security.enable').then(_ => {
driver.defaultSession.on('Security.securityStateChanged', state => { /* ... */ });
})

// WILL work! happy happy. :)
driver.defaultSession.on('Security.securityStateChanged', state => { /* ... */ }); // event binding is synchronous
driver.defaultSession.sendCommand('Security.enable');

調試協(xié)議:閱讀更好地調試協(xié)議Better debugging of the Protocol[4]。

配置passes

passes 屬性控制如何加載請求的 URL,以及在加載時收集哪些關于頁面的信息。pass 數(shù)組中的每個條目代表頁面的一次加載,

每個 pass 都定義了基本設置,例如等待頁面加載多長時間、是否記錄 trace 文件。此外,每次傳遞都定義了要使用的 gatherer 列表。gatherer 可以從頁面中讀取信息以生成 artifacts,稍后 Audits 使用這些artifacts提供 Lighthouse 報告。

具體的 pass 配置示例:

{
passes: [{
passName: 'fastPass',
atherers: ['fast-gatherer'],
},
{
passName: 'slowPass',
recordTrace: true,
useThrottling: true,
networkQuietThresholdMs: 5000,
gatherers: ['slow-gatherer'],
}]
}

Gatherers 采集器

決定在頁面加載過程中采集哪些信息,將采集的信息輸出為 artifacts。使用 Driver 采集頁面信息。用 --gather-mode 指令運行可以獲得3個采集產物:

artifacts.json: 所有采集器的輸出。

defaultPass.trace.json: 大多數(shù)性能指標。可以在DevTools性能面板中查看。

defaultPass.devtoolslog.json: DevTools Protocol[5] 事件的日志。

每一個 gatherer繼承自相同的基類 Gatherer,基類 Gatherer定義了傳遞生命周期的n個方法。 gatherer的artifacts是生命周期方法返回的最后一個未定義值,所有方法都可以直接返回artifacts或返回解析為該值的 Promise。子類只需實現(xiàn)生命周期方法即可。

比如用于js覆蓋率的 gatherer:

該實例實現(xiàn)了 startInstrumentation 、stopInstrumentation、getArtifact 3個生命周期方法,其

class JsUsage extends FRGatherer {
meta = {
supportedModes: ['snapshot', 'timespan', 'navigation'],
};

constructor() {
super();
this._scriptUsages = [];
}
async startInstrumentation(context) {
const session = context.driver.defaultSession;
await session.sendCommand('Profiler.enable');
await session.sendCommand('Profiler.startPreciseCoverage', {detailed: false});
}


async stopInstrumentation(context) {
const session = context.driver.defaultSession;
const coverageResponse = await session.sendCommand('Profiler.takePreciseCoverage');
this._scriptUsages = coverageResponse.result;
await session.sendCommand('Profiler.stopPreciseCoverage');
await session.sendCommand('Profiler.disable');
}

async getArtifact() {
const usageByScriptId = {};
for (const scriptUsage of this._scriptUsages) {
if (scriptUsage.url === '' || scriptUsage.url === '_lighthouse-eval.js') {
continue;
}
usageByScriptId[scriptUsage.scriptId] = scriptUsage;
}
return usageByScriptId;
}
}

class FRGatherer { meta = { supportedModes : []}; //在任意時間段內開始觀察頁面 startInstrumentation ( passContext ) { } //Sensitive開始觀察頁面 startSensitiveInstrumentation ( passContext ) { } //Sensitive停止觀察頁面的方法 stopSensitiveInstrumentation ( passContext ) { } //在任意時間段內結束觀察頁面 stopInstrumentation ( passContext ) { } //收集有關頁面的結果 getArtifact ( passContext ) { } /** * Legacy */ get name () {} async beforePass ( passContext ) {} pass ( passContext ) { } async afterPass ( passContext, loadData ) {}

當 pass 中定義的所有 gatherers 運行完后,就會生成一個中間產物 artifacts,此后 Lighthouse 就可以斷開與瀏覽器的連接,只使用 artifacts 進行后續(xù)的分析。

Trace 鏈路追蹤

core/lib/tracehouse/trace-processor.js提供了鏈路到更有意義對象的轉換。每個原始trace event[6] 都具有以微秒為單位增長的時間戳、線程ID、進程ID、持續(xù)時間以及其他適用的元數(shù)據(jù)屬性(比如事件類型、任務名稱、幀等)

Example Trace Event

{
'pid': 41904, // process ID
'tid': 1295, // thread ID
'ts': 1676836141, // timestamp in microseconds
'ph': 'X', // trace event type
'cat': 'toplevel', // trace category from which this event came
'name': 'MessageLoop::RunTask', // relatively human-readable description of the trace event
'dur': 64, // duration of the task in microseconds
'args': {}, // contains additional data such as frame when applicable
}

圖片

Processed trace

Processed trace 可識別關鍵時刻的 trace 事件((navigation start, FCP, LCP, DCL, trace end 等),并過濾出主進程和主線程事件的視圖。

{
processEvents: [/* all trace events in the main process */],
mainThreadEvents: [/* all trace events on the main thread */],
timings: {
timeOrigin: 0, // timeOrigin is always 0
msfirstContentfulPaint: 150, // firstContentfulPaint time in ms after time origin
/* other key moments */
traceEnd: 16420, // traceEnd time in ms after time origin
},
timestamps: {
timeOrigin: 623000000, // timeOrigin timestamp in microseconds, marks the start of the navigation of interest
firstContentfulPaint: 623150000, // firstContentfulPaint timestamp in microseconds
/* other key moments */
traceEnd: 639420000, // traceEnd timestamp in microseconds
},
}

實現(xiàn)

  1. Connecting to browser
  2. Resetting state with about:blank
  3. Navigate to about:blank
  4. Benchmarking machine
  5. Initializing…
  6. Preparing target for navigation mode
  7. Running defaultPass pass
  8. Resetting state with about:blank
  9. Navigate to about:blank
  10. Preparing target for navigation
  11. Cleaning origin data
  12. Cleaning browser cache
  13. Preparing network conditions
  14. Beginning devtoolsLog and trace
  15. Loading page & waiting for onload
  16. Navigating to https:XXX
  17. Gathering in-page: XXXXXXXX. (xN)
  18. Gathering trace
  19. Gathering devtoolsLog & network records
  20. Gathering XXX (xN)
begin();
|
→ runLighthouse();
|
→ legacyNavigation();


async function legacyNavigation(url, flags = {}, configJSON, userConnection) {
//...
const connection = userConnection || new CriConnection(flags.port, flags.hostname);
const artifacts = await Runner.gather(() => {
const requestedUrl = UrlUtils.normalizeUrl(url);
return Runner._gatherArtifactsFromBrowser(requestedUrl, options, connection);
}, options);
return Runner.audit(artifacts, options);
}

static async _gatherArtifactsFromBrowser(requestedUrl, runnerOpts, connection) {
//創(chuàng)建connection的Driver
const driver = runnerOpts.driverMock || new Driver(connection);
const gatherOpts = {
driver,
requestedUrl,
settings: runnerOpts.config.settings,
computedCache: runnerOpts.computedCache,
};
const artifacts = await GatherRunner.run(runnerOpts.config.passes, gatherOpts);
return artifacts;
}
/****** GatherRunner ****/
static async run(passConfigs, options) {


//1.Connecting to browser
//通過 Websocket 建立連接, 基于 Chrome Debugging Protocol 通信
// CDPSession 實例用于與 Chrome Devtools 協(xié)議的原生通信
await driver.connect();
// 在 devtools/extension 案例中,我們在嘗試清除狀態(tài)時仍不能在站點上
// 所以我們首先導航到 about:blank,然后應用我們的仿真和設置
// 2.Resetting state with about:blank & 3.Navigating to blankPage
await GatherRunner.loadBlank(driver);
// 4. Benchmarking machine
const baseArtifacts = await GatherRunner.initializeBaseArtifacts(options);

// ...processing benchmarkIndex

// 5. Initializing…
await GatherRunner.setupDriver(driver, options);

let isFirstPass = true;
// each pass
for (const passConfig of passConfigs) {
const passContext = {
gatherMode: 'navigation',
driver,
url: options.requestedUrl,
settings: options.settings,
passConfig,
baseArtifacts,
computedCache: options.computedCache,
LighthouseRunWarnings: baseArtifacts.LighthouseRunWarnings,
};
//Starting from about:blank, load the page and run gatherers for this pass.
const passResults = await GatherRunner.runPass(passContext);
Object.assign(artifacts, passResults.artifacts);

// If we encountered a pageLoadError, don't try to keep loading the page in future passes.
if (passResults.pageLoadError && passConfig.loadFailureMode === 'fatal') {
baseArtifacts.PageLoadError = passResults.pageLoadError;
break;
}

if (isFirstPass) {
await GatherRunner.populateBaseArtifacts(passContext);
isFirstPass = false;
}
}

await GatherRunner.disposeDriver(driver, options);
return finalizeArtifacts(baseArtifacts, artifacts);
} catch (err) {
// Clean up on error. Don't await so that the root error, not a disposal error, is shown.
GatherRunner.disposeDriver(driver, options);

throw err;
}
}

_connectToSocket(response) {
const url = response.webSocketDebuggerUrl;
this._pageId = response.id;

return new Promise((resolve, reject) => {
const ws = new WebSocket(url, {
perMessageDeflate: false,
});
ws.on('open', () => {
this._ws = ws;
resolve();
});
ws.on('message', data => this.handleRawMessage(/** @type {string} */ (data)));
ws.on('close', this.dispose.bind(this));
ws.on('error', reject);
});
}



static async setupDriver(driver, options) {
//...
await GatherRunner.assertNoSameOriginServiceWorkerClients(session, options.requestedUrl);
// 6. Preparing target for navigation mode,通過為全局 API 或錯誤處理啟用協(xié)議域、仿真和新文檔處理程序,準備在導航模式下分析的目標。
await prepare.prepareTargetForNavigationMode(driver, options.settings);
}

static async runPass(passContext) {
//7. Running defaultPass pass

const gathererResults = {};
const {driver, passConfig} = passContext;

// 8.Resetting state with about:blank 9.Navigating to about:blankGo to about:blank
// set up

await GatherRunner.loadBlank(driver, passConfig.blankPage);
// 10.Preparing target for navigation ~ 13.Preparing network conditions
const {warnings} = await prepare.prepareTargetForIndividualNavigation(
driver.defaultSession,
passContext.settings,
{
requestor: passContext.url,
disableStorageReset: !passConfig.useThrottling,
disableThrottling: !passConfig.useThrottling,
blockedUrlPatterns: passConfig.blockedUrlPatterns,
}
);
// run `startInstrumentation() /beforePass()` on gatherers.
passContext.LighthouseRunWarnings.push(...warnings);
await GatherRunner.beforePass(passContext, gathererResults);

// 14.Beginning devtoolsLog and trace,
// await driver.beginDevtoolsLog(); await driver.beginTrace(settings);
await GatherRunner.beginRecording(passContext);
//15.Loading page & waiting for onload ,16.Navigating to https:XXX
const {navigationError: possibleNavError} = await GatherRunner.loadPage(driver, passContext);
//17.Gathering in-page: XXXXXXXX,run `pass()` on gatherers.
await GatherRunner.pass(passContext, gathererResults);
const loadData = await GatherRunner.endRecording(passContext);

//18.Gathering trace 19.Gathering devtoolsLog & network records
await emulation.clearThrottling(driver.defaultSession);

//process page error

// If no error, save devtoolsLog and trace.
GatherRunner._addLoadDataToBaseArtifacts(passContext, loadData, passConfig.passName);

// 20.Gathering XXX. Run `afterPass()(stopInstrumentation -> getArtifact )` on gatherers and return collected artifacts.
await GatherRunner.afterPass(passContext, loadData, gathererResults);
const artifacts = GatherRunner.collectArtifacts(gathererResults);


return artifacts;
}

Auditing

Audits 審查器

  • Audits是對單個功能/優(yōu)化/指標的測試,Gatherer 采集的 artifacts 作為輸入,審查器會對其測試,然后得出相應的測評分數(shù)結果。
  • Computed Artifacts :根據(jù) artifacts 的需求生成,有額外的含義,經常在在多個 audits 中共享。
  • 測評結果結構:

圖片

配置

audits
  • audits 屬性控制要運行和包含在 Lighthouse 報告中的審計。 查看更多示例以了解如何將自定義審核添加到您的配置中。
  • 具體的 audits 配置示例:
{
audits: [
'first-contentful-paint',
'byte-efficiency/uses-optimized-images',
]
}

實現(xiàn)

  1. Analyzing and running audits
  2. Auditing: XXX
  3. Generating results...
async function legacyNavigation(url, flags = {}, configJSON, userConnection) {
//...
return Runner.audit(artifacts, options);
}
static async audit(artifacts, options) {

//...
//1. Analyzing and running audits &2.Auditing: XXX
const auditResultsById = await Runner._runAudits(settings, config.audits, artifacts,
lighthouseRunWarnings, computedCache);

//3.Generating results...
if (artifacts.LighthouseRunWarnings) {
lighthouseRunWarnings.push(...artifacts.LighthouseRunWarnings);
}

//....

}

Report 報告

客戶端根據(jù)生成 Audit 結果的 LHR.json (Lighthouse Result) 生成結果報告頁。評分報告,它包含了性能(Performance),訪問無障礙(Accessibility),最佳實踐(Best Practice),搜索引擎優(yōu)化(SEO),PWA(Progressive Web App)5 個部分,每一項下面又有若干小項(audit),還有詳細診斷結果和優(yōu)化建議,幫助開發(fā)者有針對性地進行優(yōu)化。

例如:在 Lighthouse 8 中,性能得分由以下幾項的得分按不同的權重相加而得:

圖片

Lighthouse 8 中性能指標權重

如何確定指標分數(shù)

以性能評分[7]為例,一旦 Lighthouse 收集完性能指標(主要以毫秒為單位報告),它會通過查看指標值在其 Lighthouse 評分分布中的位置,將每個原始指標值轉換為從 0 到 100 的指標分數(shù)。評分分布是從 HTTP Archive[8] 上真實網站性能數(shù)據(jù)的性能指標得出的對數(shù)正態(tài)分布。

圖片

FCP in HTTP Archive

Lighthouse 評分曲線模型使用 HTTPArchive 數(shù)據(jù)來確定兩個控制點,然后設置對數(shù)正態(tài)曲線的形狀。HTTPArchive 數(shù)據(jù)的第 25 個百分位數(shù)變?yōu)?50 分(中值控制點),第 8 個百分位數(shù)變?yōu)?90 分(良好/綠色控制點)。在探索下面的評分曲線圖時,請注意在 0.50 和 0.92 之間,度量值和分數(shù)之間存在近乎線性的關系。0.96 左右的分數(shù)是上面的“收益遞減點”,曲線拉開,需要越來越多的指標改進來提高已經很高的分數(shù)。

圖片

探索 TTI 的評分曲線[9]

指標得分和性能得分根據(jù)以下范圍進行著色:

0至49(紅色):差

50至89(橙色):需要改進

90至100(綠色):良好

為了提供良好的用戶體驗,網站應該努力獲得良好的分數(shù)(90-100)。

實現(xiàn)

static async audit(artifacts, options) {

//....
//conclusion of the lighthouse result object
const axeVersion = artifacts.Accessibility?.version;
const credits = {
'axe-core': axeVersion,
}
let categories = {};
if (config.categories) {
categories = ReportScoring.scoreAllCategories(config.categories, auditResultsById);
}
// Replace ICU message references with localized strings; save replaced paths in lhr.
i18nLhr.i18n.icuMessagePaths = format.replaceIcuMessages(i18nLhr, settings.locale);
// LHR has now been localized.
const lhr = /** @type {LH.Result} */ (i18nLhr);
if (settings.auditMode) {
const path = Runner._getDataSavePath(settings);
assetSaver.saveLhr(lhr, path);
}
// 生成報告
const report = ReportGenerator.generateReport(lhr, settings.output);
return {lhr, artifacts, report};
}

參考資料

[1]原理結構: https://github.com/GoogleChrome/lighthouse/blob/main/docs/architecture.md

[2]Puppeteer: https://github.com/puppeteer/puppeteer

[3]WebSocket: https://github.com/websockets/ws

[4]Better debugging of the Protocol: https://github.com/GoogleChrome/lighthouse/issues/184

[5]DevTools Protocol: https://chromedevtools.github.io/devtools-protocol/

[6]trace event: https://docs.google.com/document/d/1CvAClvFfyA5R-PhYUmn5OOQtYMH4h6I0nSsKchNAySU/preview

[7]性能評分: https://web.dev/performance-scoring/

[8]HTTP Archive: https://httparchive.org/reports/state-of-the-web

[9]探索 TTI 的評分曲線: https://www.desmos.com/calculator/o98tbeyt1t

責任編輯:武曉燕 來源: ELab團隊
相關推薦

2010-09-27 10:19:09

DHCP工作流程

2009-06-05 10:26:05

struts工作流程

2011-03-31 10:54:01

Cacti工作流程

2010-06-24 16:40:16

Bittorrent協(xié)

2010-07-28 17:19:28

ICMP協(xié)議

2010-07-13 16:21:22

FIX協(xié)議

2011-03-29 09:30:12

Cacti

2009-07-27 14:13:15

2010-06-12 17:44:19

ARP協(xié)議

2010-06-23 14:46:54

DHCP協(xié)議

2023-06-05 08:14:17

RabbitMQ兔子MQ開源

2010-08-30 09:07:12

DHCP工作流程

2009-08-07 11:10:40

Netbeans ID

2011-08-08 15:14:11

PPPOE

2012-02-01 14:02:00

蘋果產品開發(fā)

2010-08-23 10:00:49

DHCP服務器

2010-09-01 15:27:40

DHCP工作流程

2021-10-30 18:56:12

Spring工作框架

2010-07-26 14:55:56

Telnet服務器

2020-10-13 21:25:15

DevOps核心
點贊
收藏

51CTO技術棧公眾號

欧美—级在线免费片| 亚洲精品电影| 在线视频欧美精品| 色婷婷精品国产一区二区三区| 伊人成年综合网| 97久久视频| 337p日本欧洲亚洲大胆精品| 国产裸体舞一区二区三区| 午夜视频在线看| 国内成+人亚洲+欧美+综合在线| 色综合色综合久久综合频道88| 特级西西人体wwwww| 日本在线中文字幕一区二区三区| 国产精品免费看片| 成人三级视频在线观看一区二区| 免费av网站在线| 久久久久久久久久久9不雅视频| 精品盗摄一区二区三区| www日韩在线观看| 4438x成人网全国最大| 91毛片在线观看| 91福利入口| 乱子伦一区二区三区| 欧美日韩第一区| 亚洲日本欧美日韩高观看| 欧美日韩久久婷婷| 日本电影欧美片| 夜夜嗨av一区二区三区| 日韩影片在线播放| 特黄视频在线观看| 精品一区二区av| 日韩av日韩在线观看| 欧美人与禽zozzo禽性配| re久久精品视频| 精品国产免费久久| 超碰91在线播放| 国产91亚洲精品久久久| 欧美视频一二三| 免费人成自慰网站| 色网站在线看| 国产亚洲精品精华液| 国产伦精品一区二区三区高清版 | 日韩精品一区二区三区免费观影| 欧美精品一区二区三区蜜桃| 51自拍视频在线观看| 久久人体大尺度| 亚洲超碰精品一区二区| 蜜臀av.com| 在线看的av网站| 久久久www免费人成精品| 久久久www免费人成黑人精品| 精品人妻无码一区二区| 精品无人码麻豆乱码1区2区| 国产福利精品视频| av大全在线观看| 国产精品久久久亚洲一区| 久久久久久久一区二区| 欧美精品色哟哟| 欧美88av| 精品中文字幕视频| 国产av无码专区亚洲av毛网站| 999精品在线| 日韩在线视频导航| 色www亚洲国产阿娇yao| 日产午夜精品一线二线三线| 在线视频免费一区二区| 中文字幕第69页| 日韩精品午夜| 久久成人在线视频| 欧美日韩亚洲国产另类| 欧美日本二区| 91精品国产91久久久久久最新| 日本三级2019| 久久福利精品| 国产成人精品一区| 中文字幕一区二区人妻| 狠狠v欧美v日韩v亚洲ⅴ| 亚洲伊人久久综合| 亚洲毛片欧洲毛片国产一品色| 国产成人福利片| 国产免费一区| 青青久草在线| 国产精品久久久久久久久免费樱桃| 亚洲美女网站18| 国产最新在线| 亚洲第一福利视频在线| 夫妻免费无码v看片| 全球最大av网站久久| 欧美高清www午色夜在线视频| 在线播放黄色av| 国产三级精品三级在线观看国产| 日韩激情第一页| 国产三级黄色片| 欧美在线播放| 欧美一二三视频| 中文字幕日本视频| 国产精品一区免费视频| 久久国产手机看片| 日韩欧美小视频| 亚洲图片欧美视频| 99久久国产宗和精品1上映| 亚洲高清国产拍精品26u| 亚洲第一色在线| www久久久久久久| 国产精品va| 国产成人精品亚洲精品| 精品人妻一区二区三区蜜桃| 久久一日本道色综合| 一本二本三本亚洲码| 亚洲电影观看| 日韩一区二区在线免费观看| 亚洲做受高潮无遮挡| 欧美精品91| 国产精品高清网站| 欧美一级特黄aaaaaa大片在线观看| 国产日韩欧美综合一区| 日b视频免费观看| 日韩国产网站| 亚洲国产精品热久久| 日本裸体美女视频| 蘑菇福利视频一区播放| 91最新国产视频| 黄网在线免费| 偷拍亚洲欧洲综合| 男插女视频网站| 日本精品三区| 26uuu另类亚洲欧美日本老年| 99久久久无码国产精品免费| 欧美国产日韩a欧美在线观看| 岛国大片在线播放| 久久精品一级| 日韩在线观看免费网站| 台湾佬中文在线| av网站一区二区三区| 艳母动漫在线观看| 国产精品久久乐| 亚洲欧洲国产一区| 99热只有这里有精品| 风间由美一区二区三区在线观看| 影音先锋欧美在线| 四虎影视4hu4虎成人| 亚洲免费影视第一页| 国产精品99精品无码视| 国产乱理伦片在线观看夜一区| 一本色道久久99精品综合| 都市激情亚洲一区| 国产视频久久久久| 天堂网av手机版| 91在线视频观看| 波多野结衣之无限发射| 国产乱论精品| 性日韩欧美在线视频| 亚洲乱码在线观看| 亚洲最大的成人av| 中国特级黄色片| 一区二区三区午夜视频| 91精品免费视频| 国产午夜精品久久久久免费视| 欧美精品视频www在线观看| 91精品久久久久久久久久久久| 天堂午夜影视日韩欧美一区二区| 欧美一二三四五区| 视频在线日韩| 中文字幕精品在线| 国产在成人精品线拍偷自揄拍| 国产精品福利在线播放| 亚洲精品免费一区亚洲精品免费精品一区 | 国产精品久久久久蜜臀| 国产综合久久久久| 超碰在线网址| 精品少妇一区二区三区视频免付费 | 久久99热这里只有精品国产| 风流少妇一区二区三区91| 亚洲国产日韩一区二区| 午夜av免费看| 爽好久久久欧美精品| 一区二区三区我不卡| 精品麻豆剧传媒av国产九九九| 欧美伦理91i| 丰满人妻妇伦又伦精品国产| 午夜精品久久久久久久蜜桃app| 欧美bbbbb性bbbbb视频| 日韩国产成人精品| 一区二区在线高清视频| 超碰97久久| 国产精品观看在线亚洲人成网| 视频一区二区三区不卡| 欧美mv日韩mv亚洲| 天码人妻一区二区三区在线看| 欧美国产成人在线| 国产在线视频三区| 99精品热视频只有精品10| 日韩在线第一区| 一区二区三区四区高清视频| 日本免费久久高清视频| 欧美成人xxx| 亚洲精品99久久久久中文字幕| 波多野结衣一区二区三区在线 | 国产一区二区三区免费播放 | free性m.freesex欧美| 亚洲男人的天堂在线播放| 国产又黄又粗又长| 激情懂色av一区av二区av| 国产真人真事毛片视频| 成人综合在线视频| 亚洲精品视频导航| 韩日欧美一区| 亚洲精品高清国产一线久久| 久久这里只有精品一区二区| 国产有码一区二区| 欧美激情20| 不卡中文字幕av| 国产小视频在线播放| 精品少妇一区二区三区在线视频| 这里只有精品国产| 午夜精品久久久久| 国产精品99久久久久久成人| 91麻豆swag| 中国特级黄色片| 国产专区综合网| 午夜精品在线免费观看| 亚洲影院一区| 久久成人福利视频| 91精品久久久久久久蜜月| 欧美日本韩国国产| 久久夜色精品国产噜噜av小说| 91嫩草国产在线观看| 国语自产精品视频在线看抢先版结局 | 欧美日韩一二区| 超碰中文字幕在线| 亚洲亚洲人成综合网络| 国产在线一卡二卡| 国产精品久久久久影视| 中文字幕成人动漫| 2024国产精品| 日韩av无码一区二区三区不卡| 国产真实精品久久二三区| 91网址在线播放| 久久精品亚洲| 欧美视频第三页| 中国女人久久久| 久久久性生活视频| 韩日精品在线| 欧美日韩福利在线| 国产精品99一区二区| a级网站在线观看| 久久久五月天| 玖玖精品在线视频| 亚洲h色精品| 只有这里有精品| 无需播放器亚洲| 中文字幕在线亚洲精品| 成人无号精品一区二区三区| 亚洲不卡一卡2卡三卡4卡5卡精品| 欧美成人午夜77777| 狠狠色噜噜狠狠狠狠色吗综合| 国产精品超碰| 精品国产乱码久久久久久88av| 久久中文字幕导航| 久久免费视频1| 亚洲欧洲免费| 亚洲成人自拍| 日韩在线观看| 99精品一区二区三区的区别| 在线免费观看日本欧美爱情大片| 波多野结衣 作品| 亚洲欧洲综合| 欧美网站免费观看| 日精品一区二区| 国产精品视频中文字幕| 精东粉嫩av免费一区二区三区| 亚洲男人天堂2021| 成人一区二区三区在线观看| 添女人荫蒂视频| 国产日本欧美一区二区| 日本女人性生活视频| 亚洲精品成人少妇| 成人免费区一区二区三区| 日本高清不卡aⅴ免费网站| 在线观看免费高清视频| 日韩一区二区免费高清| 免费看日韩av| 国产性猛交xxxx免费看久久| 爆操欧美美女| 97av在线视频免费播放| 国产一区二区三区影视| 亚洲一区二区免费| 色吊丝一区二区| 一区在线电影| 精久久久久久| 男女无套免费视频网站动漫| 韩国v欧美v日本v亚洲v| 无码精品一区二区三区在线播放| 国产精品天天看| 国产真实夫妇交换视频| 在线亚洲一区观看| www.看毛片| 国产亚洲成精品久久| 一色桃子av在线| 国产成人精品免高潮费视频| 天堂av一区| 日韩成人av电影在线| 欧美福利影院| 国产精品无码一本二本三本色| 国产伦精品一区二区三区免费迷 | 亚洲欧美在线高清| 日本三级片在线观看| 欧美男人的天堂一二区| 污污网站免费在线观看| 久久精品一区中文字幕| 自拍偷拍亚洲视频| 97netav| 日本欧美国产| 成人毛片一区二区| 91精品小视频| 国产黄人亚洲片| 国产伦精品一区二区三区视频女| 一区二区三区自拍| 久草视频在线免费| 精品毛片乱码1区2区3区| 成人免费在线电影| 久久理论片午夜琪琪电影网| 伊人久久大香伊蕉在人线观看热v 伊人久久大香线蕉综合影院首页 伊人久久大香 | 国产精品欧美在线| 加勒比色综合久久久久久久久| 亚洲一区二区在| 欧美资源在线| 亚洲精品在线视频免费观看| 亚洲综合精品久久| 一卡二卡三卡在线观看| 亚洲欧美制服第一页| 69av成人| 成人av蜜桃| 欧美 亚欧 日韩视频在线 | 日韩成人一区二区三区| 日韩一区二区在线观看视频 | 久久久久久久999精品视频| 99tv成人影院| 正在播放亚洲| 久久精品国产精品青草| 久久久免费看片| 在线免费av一区| 国内在线精品| 日韩男女性生活视频| 亚洲福利天堂| 97超碰青青草| www久久精品| 亚洲久久在线观看| 亚洲精品天天看| sis001欧美| 久久免费99精品久久久久久| 另类亚洲自拍| 欧洲av一区二区三区| 在线观看免费视频综合| 国产在线你懂得| 国产精品成久久久久三级| 欧洲美女日日| 日韩一级理论片| 欧美国产日韩a欧美在线观看 | 精品国产一区二区精华| 黑人精品视频| 精品国产一区二区三区免费| 午夜在线一区二区| www..com.cn蕾丝视频在线观看免费版| 在线观看区一区二| 天堂地址在线www| 91在线中文字幕| 极品尤物久久久av免费看| 久久精品女同亚洲女同13| 欧美午夜久久久| 番号在线播放| 91久久在线观看| 影音先锋在线一区| 亚洲最大成人网站| 欧美性猛交xxxx黑人交| 久久77777| 国产欧美日韩亚洲| 日韩av高清在线观看| 在线观看亚洲网站| 亚洲第一精品电影| 视频一区在线免费看| 91九色国产ts另类人妖| 不卡的av在线| 中文字幕第99页| 精品中文字幕视频| 三级小说欧洲区亚洲区| 国产3p在线播放| 亚洲高清三级视频| 成年网站在线| 99中文视频在线| 久久一区精品| 国产免费久久久久| 日韩精品极品在线观看| 99热这里有精品| 日韩精品一区二区三区久久| 国产精品国产a级| 手机看片国产1024| 成人激情视频小说免费下载| 99热免费精品在线观看| 国精产品久拍自产在线网站|