中文亚洲精品无码_熟女乱子伦免费_人人超碰人人爱国产_亚洲熟妇女综合网

當(dāng)前位置: 首頁(yè) > news >正文

闡述電子商務(wù)網(wǎng)站的建設(shè)要求深圳網(wǎng)絡(luò)推廣建站

闡述電子商務(wù)網(wǎng)站的建設(shè)要求,深圳網(wǎng)絡(luò)推廣建站,哈爾濱網(wǎng)站制作案例,做網(wǎng)站先做前端好還是先做邏輯1.模塊依賴2. 模塊的初始化2.1 location的定義location的定義包含以下幾種location [ | ~ | ~* | ^~ ] uri { ... } location name { ... }:表示精確匹配,只有請(qǐng)求的url路徑與后面的字符串完全相等時(shí),才會(huì)命中,不支持location嵌套~&#xff…

1.模塊依賴

2. 模塊的初始化

2.1 location的定義

location的定義包含以下幾種

location [ = | ~ | ~* | ^~ ] uri { ... }
location @name { ... }

=:表示精確匹配,只有請(qǐng)求的url路徑與后面的字符串完全相等時(shí),才會(huì)命中,不支持location嵌套

~:表示使用正則定義的,區(qū)分大小寫

~*:表示是使用正則定義的,不區(qū)分大小寫

^~:表示該符號(hào)后面的字符是最佳匹配,采用該規(guī)則,不再進(jìn)行后續(xù)的查找

@name:用于定義一個(gè)內(nèi)部 Location 塊,該塊不能被外部 Client 所訪問,只能被 NGINX 內(nèi)部配置指令所訪問,比如 try_files 或者error_page。其修飾的location不能嵌套到其它location,也不能再嵌套其它location,即只能是server這一層的

2.2 分配ngx_http_conf_ctx_t

2.2.1 ngx_http_block

其是在解析配置文件中的http分配

ctx = ngx_pcalloc(cf->pool, sizeof(ngx_http_conf_ctx_t));
ctx->main_conf = ngx_pcalloc(cf->pool,sizeof(void *) * ngx_http_max_module);
ctx->srv_conf = ngx_pcalloc(cf->pool, sizeof(void *) * ngx_http_max_module);
ctx->loc_conf = ngx_pcalloc(cf->pool, sizeof(void *) * ngx_http_max_module);

2.2.2 ngx_http_core_location

其是在解析配置文件中的http塊內(nèi)location時(shí)分配

其中main_conf,srv_conf是延用上一層級(jí)的,loc_conf會(huì)再一次分配內(nèi)存

ctx = ngx_pcalloc(cf->pool, sizeof(ngx_http_conf_ctx_t));
pctx = cf->ctx;
ctx->main_conf = pctx->main_conf;
ctx->srv_conf = pctx->srv_conf;
ctx->loc_conf = ngx_pcalloc(cf->pool, sizeof(void *) * ngx_http_max_module);

同時(shí)也會(huì)遍歷模塊調(diào)用create_loc_conf創(chuàng)建location的配置

for (i = 0; cf->cycle->modules[i]; i++) {if (cf->cycle->modules[i]->type != NGX_HTTP_MODULE) {continue;}module = cf->cycle->modules[i]->ctx;if (module->create_loc_conf) {ctx->loc_conf[cf->cycle->modules[i]->ctx_index] =module->create_loc_conf(cf);if (ctx->loc_conf[cf->cycle->modules[i]->ctx_index] == NULL) {return NGX_CONF_ERROR;}}}

設(shè)置http_core_module配置的loc_conf來源

clcf = ctx->loc_conf[ngx_http_core_module.ctx_index];
clcf->loc_conf = ctx->loc_conf;

2.3 ngx_http_add_location

構(gòu)造ngx_http_location_queue_t,將當(dāng)前ngx_http_core_loc_conf_t添加到上一層級(jí)ngx_http_core_loc_conf_t中的location隊(duì)列中。如果是精確匹配,正則,有名或者是無名,構(gòu)造的ngx_http_location_queue_t的exact來存放ngx_http_core_loc_conf_t配置,否則使用ngx_http_location_queue_t的inclusive來存放ngx_http_core_loc_conf_t配置

if (clcf->exact_match
#if (NGX_PCRE)|| clcf->regex
#endif|| clcf->named || clcf->noname){lq->exact = clcf;lq->inclusive = NULL;} else {lq->exact = NULL;lq->inclusive = clcf;}

將構(gòu)造的隊(duì)列添加到上一層級(jí)的隊(duì)列中

ngx_queue_insert_tail(*locations, &lq->queue);

2.4 主配置中的server

在ngx_http_block中會(huì)分配main_conf

ctx->main_conf = ngx_pcalloc(cf->pool,sizeof(void *) * ngx_http_max_module);

在處理server時(shí)(ngx_http_core_server),當(dāng)前層的ctx中的main_conf會(huì)延用上一層的main_conf

http_ctx = cf->ctx;
ctx->main_conf = http_ctx->main_conf;

將server放入cmcf->server中

cscf = ctx->srv_conf[ngx_http_core_module.ctx_index];
cscf->ctx = ctx;cmcf = ctx->main_conf[ngx_http_core_module.ctx_index];cscfp = ngx_array_push(&cmcf->servers);
if (cscfp == NULL) {return NGX_CONF_ERROR;
}*cscfp = cscf;

2.5 初始化location(ngx_http_init_locations)

處理ngx_http_core_srv_conf_t中的有名location(named_locations)以及ngx_http_core_loc_conf_t中的正則location(regex_locations),在作割裂之前,會(huì)先對(duì)ngx_http_core_loc_conf_t中的locations排序,使用的排序規(guī)則為ngx_http_cmp_locations,即按照exact(sorted) -> inclusive(sorted) -> regex -> named -> noname的原則進(jìn)行排序,經(jīng)過處理后,原先的location隊(duì)列就只剩下經(jīng)過排序后的exact以及inclusive類型的location了。這兩類location對(duì)應(yīng)配置文件中的定義,就是不含修飾符的location,帶有=和^~前綴的location。

2.6 將queue轉(zhuǎn)為list(ngx_http_create_locations_list)

將locations queue變成locations list

2.7 創(chuàng)建location的二叉查找樹(ngx_http_create_locations_tree)

創(chuàng)建精確匹配location的二叉查找樹,使用ngx_queue_middle(其時(shí)間度為O(n))得到location_list中的中間位置,如果location_list的元素個(gè)數(shù)為奇數(shù),則是中間的一個(gè),否則是后半部分的第一個(gè)。

ngx_queue_t *
ngx_queue_middle(ngx_queue_t *queue)
{ngx_queue_t  *middle, *next;middle = ngx_queue_head(queue);if (middle == ngx_queue_last(queue)) {return middle;}next = ngx_queue_head(queue);for ( ;; ) {middle = ngx_queue_next(middle);next = ngx_queue_next(next);if (next == ngx_queue_last(queue)) {return middle;}next = ngx_queue_next(next);if (next == ngx_queue_last(queue)) {return middle;}}
}

使用遞歸來構(gòu)建二叉查找樹

/** to keep cache locality for left leaf nodes, allocate nodes in following* order: node, left subtree, right subtree, inclusive subtree*/static ngx_http_location_tree_node_t *
ngx_http_create_locations_tree(ngx_conf_t *cf, ngx_queue_t *locations,size_t prefix)
{size_t                          len;ngx_queue_t                    *q, tail;ngx_http_location_queue_t      *lq;ngx_http_location_tree_node_t  *node;q = ngx_queue_middle(locations);lq = (ngx_http_location_queue_t *) q;len = lq->name->len - prefix;node = ngx_palloc(cf->pool,offsetof(ngx_http_location_tree_node_t, name) + len);if (node == NULL) {return NULL;}node->left = NULL;node->right = NULL;node->tree = NULL;node->exact = lq->exact;node->inclusive = lq->inclusive;node->auto_redirect = (u_char) ((lq->exact && lq->exact->auto_redirect)|| (lq->inclusive && lq->inclusive->auto_redirect));node->len = (u_short) len;ngx_memcpy(node->name, &lq->name->data[prefix], len);ngx_queue_split(locations, q, &tail);if (ngx_queue_empty(locations)) {/** ngx_queue_split() insures that if left part is empty,* then right one is empty too*/goto inclusive;}node->left = ngx_http_create_locations_tree(cf, locations, prefix);if (node->left == NULL) {return NULL;}ngx_queue_remove(q);if (ngx_queue_empty(&tail)) {goto inclusive;}node->right = ngx_http_create_locations_tree(cf, &tail, prefix);if (node->right == NULL) {return NULL;}inclusive:if (ngx_queue_empty(&lq->list)) {return node;}node->tree = ngx_http_create_locations_tree(cf, &lq->list, prefix + len);if (node->tree == NULL) {return NULL;}return node;
}

2.8 http的處理階段

包含11個(gè)階段

枚舉

名稱

NGX_HTTP_POST_READ_PHASE

在接收到完整的HTTP頭部后處理的HTTP階段

NGX_HTTP_SERVER_REWRITE_PHASE

在將請(qǐng)求的URI與location表達(dá)式匹配前, 修改請(qǐng)求的URI(所謂的重定向) 是一個(gè)獨(dú)立的HTTP階段

NGX_HTTP_FIND_CONFIG_PHASE

根據(jù)請(qǐng)求的URI尋找匹配的location表達(dá)式, 這個(gè)階段只能由ngx_http_core_module模塊實(shí)現(xiàn), 不建議其他HTTP模塊重新定義這一階段的行為

NGX_HTTP_REWRITE_PHASE

在NGX_HTTP_FIND_CONFIG_PHASE階段尋找到匹配的location之后再修改請(qǐng)求的URI

NGX_HTTP_POST_REWRITE_PHASE

這一階段是用于在rewrite重寫URL后, 防止錯(cuò)誤的

nginx.conf配置導(dǎo)致死循環(huán)(遞歸地修改URI) , 因此, 這一階段僅由ngx_http_core_module模塊處理。 目前, 控制死循環(huán)的方式很簡(jiǎn)單, 首先檢查

rewrite的次數(shù), 如果一個(gè)請(qǐng)求超過10次重定向

,就認(rèn)為進(jìn)入了rewrite死循環(huán), 這時(shí)在

NGX_HTTP_POST_REWRITE_PHASE階段就會(huì)向用戶返回500, 表示服務(wù)器內(nèi)部錯(cuò)誤

NGX_HTTP_PREACCESS_PHASE

表示在處理NGX_HTTP_ACCESS_PHASE階段決定請(qǐng)求的訪問權(quán)限前HTTP模塊可以介入的處理階段

NGX_HTTP_ACCESS_PHASE

這個(gè)階段用于讓HTTP模塊判斷是否允許這個(gè)請(qǐng)求訪問

Nginx服務(wù)器

NGX_HTTP_POST_ACCESS_PHASE

在NGX_HTTP_ACCESS_PHASE階段中, 當(dāng)

HTTP模塊的handler處理函數(shù)返回不允許訪問的錯(cuò)誤碼時(shí)(實(shí)際就是NGX_HTTP_FORBIDDEN或者

NGX_HTTP_UNAUTHORIZED) , 這里將負(fù)責(zé)向用戶發(fā)送拒絕服務(wù)的錯(cuò)誤響應(yīng)。 因此, 這個(gè)階段實(shí)際上用于給NGX_HTTP_ACCESS_PHASE階段收尾

NGX_HTTP_PRECONTENT_PHASE

http請(qǐng)求內(nèi)容前置處理

NGX_HTTP_CONTENT_PHASE

用于處理HTTP請(qǐng)求內(nèi)容的階段, 這是大部分

HTTP模塊最愿意介入的階段

NGX_HTTP_LOG_PHASE

處理完請(qǐng)求后記錄日志的階段

2.9 階段處理器的初始化

ngx_http_init_phases初始化以下階段的handlers

  • NGX_HTTP_POST_READ_PHASE

  • NGX_HTTP_SERVER_REWRITE_PHASE

  • NGX_HTTP_REWRITE_PHASE

  • NGX_HTTP_PREACCESS_PHASE

  • NGX_HTTP_ACCESS_PHASE

  • NGX_HTTP_PRECONTENT_PHASE

  • NGX_HTTP_CONTENT_PHASE

  • NGX_HTTP_LOG_PHASE

static ngx_int_t
ngx_http_init_phases(ngx_conf_t *cf, ngx_http_core_main_conf_t *cmcf)
{if (ngx_array_init(&cmcf->phases[NGX_HTTP_POST_READ_PHASE].handlers,cf->pool, 1, sizeof(ngx_http_handler_pt))!= NGX_OK){return NGX_ERROR;}if (ngx_array_init(&cmcf->phases[NGX_HTTP_SERVER_REWRITE_PHASE].handlers,cf->pool, 1, sizeof(ngx_http_handler_pt))!= NGX_OK){return NGX_ERROR;}if (ngx_array_init(&cmcf->phases[NGX_HTTP_REWRITE_PHASE].handlers,cf->pool, 1, sizeof(ngx_http_handler_pt))!= NGX_OK){return NGX_ERROR;}if (ngx_array_init(&cmcf->phases[NGX_HTTP_PREACCESS_PHASE].handlers,cf->pool, 1, sizeof(ngx_http_handler_pt))!= NGX_OK){return NGX_ERROR;}if (ngx_array_init(&cmcf->phases[NGX_HTTP_ACCESS_PHASE].handlers,cf->pool, 2, sizeof(ngx_http_handler_pt))!= NGX_OK){return NGX_ERROR;}if (ngx_array_init(&cmcf->phases[NGX_HTTP_PRECONTENT_PHASE].handlers,cf->pool, 2, sizeof(ngx_http_handler_pt))!= NGX_OK){return NGX_ERROR;}if (ngx_array_init(&cmcf->phases[NGX_HTTP_CONTENT_PHASE].handlers,cf->pool, 4, sizeof(ngx_http_handler_pt))!= NGX_OK){return NGX_ERROR;}if (ngx_array_init(&cmcf->phases[NGX_HTTP_LOG_PHASE].handlers,cf->pool, 1, sizeof(ngx_http_handler_pt))!= NGX_OK){return NGX_ERROR;}return NGX_OK;
}

2.10 配置后置處理(postconfiguration)

遍歷調(diào)用http模塊的postconfiguration,用來注冊(cè)階段的handler

for (m = 0; cf->cycle->modules[m]; m++) {if (cf->cycle->modules[m]->type != NGX_HTTP_MODULE) {continue;}module = cf->cycle->modules[m]->ctx;if (module->postconfiguration) {if (module->postconfiguration(cf) != NGX_OK) {return NGX_CONF_ERROR;}}}

2.11 階段引擎handler的初始化

將各個(gè)不同階段的handler匯聚成一個(gè)處理鏈表

static ngx_int_t
ngx_http_init_phase_handlers(ngx_conf_t *cf, ngx_http_core_main_conf_t *cmcf)
{ngx_int_t                   j;ngx_uint_t                  i, n;ngx_uint_t                  find_config_index, use_rewrite, use_access;ngx_http_handler_pt        *h;ngx_http_phase_handler_t   *ph;ngx_http_phase_handler_pt   checker;cmcf->phase_engine.server_rewrite_index = (ngx_uint_t) -1;cmcf->phase_engine.location_rewrite_index = (ngx_uint_t) -1;find_config_index = 0;use_rewrite = cmcf->phases[NGX_HTTP_REWRITE_PHASE].handlers.nelts ? 1 : 0;use_access = cmcf->phases[NGX_HTTP_ACCESS_PHASE].handlers.nelts ? 1 : 0;n = 1                  /* find config phase */+ use_rewrite      /* post rewrite phase */+ use_access;      /* post access phase */for (i = 0; i < NGX_HTTP_LOG_PHASE; i++) {n += cmcf->phases[i].handlers.nelts;}ph = ngx_pcalloc(cf->pool,n * sizeof(ngx_http_phase_handler_t) + sizeof(void *));if (ph == NULL) {return NGX_ERROR;}cmcf->phase_engine.handlers = ph;n = 0;for (i = 0; i < NGX_HTTP_LOG_PHASE; i++) {h = cmcf->phases[i].handlers.elts;switch (i) {case NGX_HTTP_SERVER_REWRITE_PHASE:if (cmcf->phase_engine.server_rewrite_index == (ngx_uint_t) -1) {cmcf->phase_engine.server_rewrite_index = n;}checker = ngx_http_core_rewrite_phase;break;case NGX_HTTP_FIND_CONFIG_PHASE:find_config_index = n;ph->checker = ngx_http_core_find_config_phase;n++;ph++;continue;case NGX_HTTP_REWRITE_PHASE:if (cmcf->phase_engine.location_rewrite_index == (ngx_uint_t) -1) {cmcf->phase_engine.location_rewrite_index = n;}checker = ngx_http_core_rewrite_phase;break;case NGX_HTTP_POST_REWRITE_PHASE:if (use_rewrite) {ph->checker = ngx_http_core_post_rewrite_phase;ph->next = find_config_index;n++;ph++;}continue;case NGX_HTTP_ACCESS_PHASE:checker = ngx_http_core_access_phase;n++;break;case NGX_HTTP_POST_ACCESS_PHASE:if (use_access) {ph->checker = ngx_http_core_post_access_phase;ph->next = n;ph++;}continue;case NGX_HTTP_CONTENT_PHASE:checker = ngx_http_core_content_phase;break;default:checker = ngx_http_core_generic_phase;}n += cmcf->phases[i].handlers.nelts;for (j = cmcf->phases[i].handlers.nelts - 1; j >= 0; j--) {ph->checker = checker;ph->handler = h[j];ph->next = n;ph++;}}return NGX_OK;
}

2.12 初始監(jiān)聽端口, 服務(wù)以及監(jiān)聽回調(diào)

ngx_http_optimize_servers中的ngx_http_add_listening會(huì)設(shè)置端口的回調(diào)

ls->handler = ngx_http_init_connection;

3. 運(yùn)行時(shí)的處理

3.1 accept事件處理

在處理accept連接事件時(shí),會(huì)調(diào)用ngx_listening_t的回調(diào)handler函數(shù)ngx_http_init_connection

對(duì)于新分配的連接,如果讀事件的ready為1,即iocp或者延時(shí)的accept事件,在有使用accept鎖情況 下,將事件放入posted_events隊(duì)列中,否則直接調(diào)用事件的回調(diào)handler

if (rev->ready) {/* the deferred accept(), iocp */if (ngx_use_accept_mutex) {ngx_post_event(rev, &ngx_posted_events);return;}rev->handler(rev);return;
}

如果讀事件的ready不為1,則將事件加入定時(shí)器的紅黑樹中。定時(shí)器超時(shí)后,就會(huì)調(diào)用它的 handler ngx_http_wait_request_handler 函數(shù)。

ngx_add_timer(rev, cscf->client_header_timeout);

將連接設(shè)置為可重用,因?yàn)樵撨B接上還沒有請(qǐng)求到來,所以當(dāng)連接池中的連接不夠用時(shí),就可以重用這個(gè)連接。將當(dāng)前connection添加可重用的連接隊(duì)列中,同時(shí)可重用連接數(shù)加1

ngx_reusable_connection(c, 1);void
ngx_reusable_connection(ngx_connection_t *c, ngx_uint_t reusable)
{ngx_log_debug1(NGX_LOG_DEBUG_CORE, c->log, 0,"reusable connection: %ui", reusable);if (c->reusable) {ngx_queue_remove(&c->queue);ngx_cycle->reusable_connections_n--;#if (NGX_STAT_STUB)(void) ngx_atomic_fetch_add(ngx_stat_waiting, -1);
#endif}c->reusable = reusable;if (reusable) {/* need cast as ngx_cycle is volatile */ngx_queue_insert_head((ngx_queue_t *) &ngx_cycle->reusable_connections_queue, &c->queue);ngx_cycle->reusable_connections_n++;#if (NGX_STAT_STUB)(void) ngx_atomic_fetch_add(ngx_stat_waiting, 1);
#endif}
}

ngx_handle_read_event將分配連接的事件添加到事件驅(qū)動(dòng)模塊中

ngx_int_t
ngx_handle_read_event(ngx_event_t *rev, ngx_uint_t flags)
{if (ngx_event_flags & NGX_USE_CLEAR_EVENT) {/* kqueue, epoll */if (!rev->active && !rev->ready) {if (ngx_add_event(rev, NGX_READ_EVENT, NGX_CLEAR_EVENT)== NGX_ERROR){return NGX_ERROR;}}return NGX_OK;} else if (ngx_event_flags & NGX_USE_LEVEL_EVENT) {/* select, poll, /dev/poll */if (!rev->active && !rev->ready) {if (ngx_add_event(rev, NGX_READ_EVENT, NGX_LEVEL_EVENT)== NGX_ERROR){return NGX_ERROR;}return NGX_OK;}if (rev->active && (rev->ready || (flags & NGX_CLOSE_EVENT))) {if (ngx_del_event(rev, NGX_READ_EVENT, NGX_LEVEL_EVENT | flags)== NGX_ERROR){return NGX_ERROR;}return NGX_OK;}} else if (ngx_event_flags & NGX_USE_EVENTPORT_EVENT) {/* event ports */if (!rev->active && !rev->ready) {if (ngx_add_event(rev, NGX_READ_EVENT, 0) == NGX_ERROR) {return NGX_ERROR;}return NGX_OK;}if (rev->oneshot && rev->ready) {if (ngx_del_event(rev, NGX_READ_EVENT, 0) == NGX_ERROR) {return NGX_ERROR;}return NGX_OK;}}/* iocp */return NGX_OK;
}

3.2 首次可讀事件處理

是通過ngx_http_wait_request_handler來處理

首先從網(wǎng)絡(luò)上讀取數(shù)據(jù)到連接中的buffer

ngx_connection_t          *c;
ngx_buf_t                 *b;
c = rev->data;
b = c->buffer;
if (b == NULL) {b = ngx_create_temp_buf(c->pool, size);if (b == NULL) {ngx_http_close_connection(c);return;}c->buffer = b;} else if (b->start == NULL) {b->start = ngx_palloc(c->pool, size);if (b->start == NULL) {ngx_http_close_connection(c);return;}b->pos = b->start;b->last = b->start;b->end = b->last + size;
}
n = c->recv(c, b->last, size);
b->last += n;

在可重用連接中刪除當(dāng)前連接

ngx_reusable_connection(c, 0);

創(chuàng)建http_request,在創(chuàng)建請(qǐng)求中,會(huì)將上面讀取的緩沖區(qū)放在ngx_http_request_t中的header_in用于處理請(qǐng)求頭

c->data = ngx_http_create_request(c);

處理請(qǐng)求頭,同時(shí)將當(dāng)前連接讀事件的回調(diào)函數(shù)設(shè)置為ngx_http_process_request_line,用于處理單次接收的數(shù)據(jù)不完整

rev->handler = ngx_http_process_request_line;
ngx_http_process_request_line(rev);

3.3 請(qǐng)求行的處理

是通過ngx_http_process_request_line來處理的

先解析請(qǐng)求行

rc = ngx_http_parse_request_line(r, r->header_in);
http://www.risenshineclean.com/news/60502.html

相關(guān)文章:

  • 網(wǎng)站首頁(yè) 排版網(wǎng)絡(luò)營(yíng)銷課程總結(jié)
  • 商業(yè)網(wǎng)站開發(fā)選題的目的哪些平臺(tái)可以做推廣
  • 王也諸葛青sem優(yōu)化軟件選哪家
  • 電子商務(wù)網(wǎng)站分析百度快照是干嘛的
  • 營(yíng)銷型企業(yè)網(wǎng)站的功能網(wǎng)絡(luò)廣告營(yíng)銷方案策劃內(nèi)容
  • 建設(shè)一個(gè)網(wǎng)站用什么搭建北京搜索排名優(yōu)化
  • 政府 網(wǎng)站建設(shè)方案推廣產(chǎn)品
  • 滑縣做網(wǎng)站公司制作網(wǎng)頁(yè)的基本步驟
  • 網(wǎng)站上的qq如何做懸浮百度seo公司
  • 企業(yè)網(wǎng)站排名怎么優(yōu)化西安網(wǎng)站建設(shè)公司電話
  • flash網(wǎng)站 seo常見的推廣方式
  • 我要建設(shè)一個(gè)網(wǎng)站微信小程序開發(fā)費(fèi)用一覽表
  • 中華人民共和國(guó)住房建設(shè)部網(wǎng)站seo自學(xué)網(wǎng)官網(wǎng)
  • 做美食如何加入團(tuán)購(gòu)網(wǎng)站網(wǎng)絡(luò)推廣的渠道
  • 蕭山區(qū)建設(shè)工程質(zhì)量監(jiān)督站網(wǎng)站長(zhǎng)沙百度關(guān)鍵詞推廣
  • 銅山區(qū)建設(shè)局局網(wǎng)站網(wǎng)站網(wǎng)頁(yè)設(shè)計(jì)
  • 南京建設(shè)監(jiān)理協(xié)會(huì)網(wǎng)站臨沂seo公司穩(wěn)健火星
  • 做網(wǎng)站用哪個(gè)軟件公司域名注冊(cè)查詢
  • 十大搞笑素材網(wǎng)站搜索引擎優(yōu)化技巧
  • 經(jīng)營(yíng)購(gòu)物網(wǎng)站市場(chǎng)營(yíng)銷推廣方案模板
  • 海南做公司網(wǎng)站seo技巧分享
  • 做營(yíng)銷最好的網(wǎng)站源碼愛營(yíng)銷電信版下載app最新版
  • 網(wǎng)站建設(shè)用英語怎么說排名優(yōu)化公司口碑哪家好
  • 網(wǎng)站開發(fā) 國(guó)際網(wǎng)站國(guó)外黃岡網(wǎng)站推廣軟件
  • 北京專業(yè)建設(shè)網(wǎng)站價(jià)格排名第一的手機(jī)清理軟件
  • 網(wǎng)站模板怎么建站新東方在線教育平臺(tái)官網(wǎng)
  • 肅寧做網(wǎng)站湖南優(yōu)化電商服務(wù)有限公司
  • 上海速恒網(wǎng)絡(luò)科技有限公司天津seo優(yōu)化公司
  • 英文b2c網(wǎng)站營(yíng)銷技巧有哪些
  • 做網(wǎng)站公司哪個(gè)好百度免費(fèi)推廣平臺(tái)