搜索引擎如何处理AngularJS应用程序?

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了搜索引擎如何处理AngularJS应用程序?相关的知识,希望对你有一定的参考价值。

我看到AngularJS应用程序有关搜索引擎和搜索引擎优化的两个问题:

1)自定义标签会发生什么?搜索引擎会忽略这些标签中的所有内容吗?即假设我有

<custom>
  <h1>Hey, this title is important</h1>
</custom>

将Qazxswpoi归类为自定义标签内部吗?

2)有没有办法避免索引{{}}的搜索引擎字面上绑定?即

<h1>

我知道我可以做点什么

<h2>{{title}}</h2>

但是,如果我想让爬虫“看到”标题怎么办?服务器端渲染是唯一的解决方案吗?

答案

2014年5月更新

Google抓取工具<h2 ng-bind="title"></h2> - 您可以使用now executes javascript更好地了解Google如何呈现您的网站。

原始答案 如果您想针对搜索引擎优化您的应用,很遗憾无法为抓取工具提供预渲染版本。您可以阅读更多关于Google对ajax和javascript-heavy网站Google Webmaster Tools的建议。

如果这是一个选项,我建议阅读here关于如何使用服务器端渲染为Angular做SEO。

我不确定爬虫在遇到自定义标签时会做什么。

另一答案

Google的Crawlable Ajax Spec,在其他答案中引用,基本上就是答案。

如果你对其他搜索引擎和社交机器人如何处理同样的问题感兴趣,我在这里写下了艺术现状:Times have changed. Today, as long as you're not blocking Googlebot from crawling your JavaScript or CSS files, we are generally able to render and understand your web pages like modern browsers.

我为http://blog.ajaxsnapshots.com/2013/11/googles-crawlable-ajax-specification.html工作,这是一家实现Crawlable Ajax Spec作为服务的公司 - 该报告中的信息基于我们日志的观察结果。

另一答案

我找到了一个优雅的解决方案,可以覆盖你的大部分基地。我最初写了https://ajaxsnapshots.com并回答了另一个类似的StackOverflow问题here,它引用了它。

仅供参考,此解决方案还包括硬编码的回退标记,以防爬虫无法获取Javascript。我没有明确地概述它,但值得一提的是,您应该激活html5模式以获得正确的URL支持。

另请注意:这些不是完整的文件,只是相关部分的重要部分。如果您需要帮助编写可在其他地方找到的指令,服务等的样板文件。无论如何,这里......

app.js

您可以在此处为每条路线提供自定义元数据(标题,说明等)

here

metadata-service.js(服务)

设置自定义元数据选项或使用默认值作为回退。

$routeProvider
   .when('/', {
       templateUrl: 'views/homepage.html',
       controller: 'HomepageCtrl',
       metadata: {
           title: 'The Base Page Title',
           description: 'The Base Page Description' }
   })
   .when('/about', {
       templateUrl: 'views/about.html',
       controller: 'AboutCtrl',
       metadata: {
           title: 'The About Page Title',
           description: 'The About Page Description' }
   })

metaproperty.js(指令)

打包视图的元数据服务结果。

var self = this;

// Set custom options or use provided fallback (default) options
self.loadMetadata = function(metadata) {
  self.title = document.title = metadata.title || 'Fallback Title';
  self.description = metadata.description || 'Fallback Description';
  self.url = metadata.url || $location.absUrl();
  self.image = metadata.image || 'fallbackimage.jpg';
  self.ogpType = metadata.ogpType || 'website';
  self.twitterCard = metadata.twitterCard || 'summary_large_image';
  self.twitterSite = metadata.twitterSite || '@fallback_handle';
};

// Route change handler, sets the route's defined metadata
$rootScope.$on('$routeChangeSuccess', function (event, newRoute) {
  self.loadMetadata(newRoute.metadata);
});

的index.html

完成前面提到的硬编码后备标记,对于无法获取任何Javascript的抓取工具。

return {
  restrict: 'A',
  scope: {
    metaproperty: '@'
  },
  link: function postLink(scope, element, attrs) {
    scope.default = element.attr('content');
    scope.metadata = metadataService;

    // Watch for metadata changes and set content
    scope.$watch('metadata', function (newVal, oldVal) {
      setContent(newVal);
    }, true);

    // Set the content attribute with new metadataService value or back to the default
    function setContent(metadata) {
      var content = metadata[scope.metaproperty] || scope.default;
      element.attr('content', content);
    }

    setContent(scope.metadata);
  }
};

这应该对大多数搜索引擎用例有很大帮助。如果您想要社交网络抓取工具(在Javascript支持上不受欢迎)的完全动态渲染,您仍然必须使用其他一些答案中提到的预渲染服务之一。

希望这可以帮助!

另一答案

使用类似PreRender的东西,它会生成您网站的静态页面,以便搜索引擎可以为其编制索引。

在这里,您可以找到它可用的平台:<head> <title>Fallback Title</title> <meta name="description" metaproperty="description" content="Fallback Description"> <!-- Open Graph Protocol Tags --> <meta property="og:url" content="fallbackurl.com" metaproperty="url"> <meta property="og:title" content="Fallback Title" metaproperty="title"> <meta property="og:description" content="Fallback Description" metaproperty="description"> <meta property="og:type" content="website" metaproperty="ogpType"> <meta property="og:image" content="fallbackimage.jpg" metaproperty="image"> <!-- Twitter Card Tags --> <meta name="twitter:card" content="summary_large_image" metaproperty="twitterCard"> <meta name="twitter:title" content="Fallback Title" metaproperty="title"> <meta name="twitter:description" content="Fallback Description" metaproperty="description"> <meta name="twitter:site" content="@fallback_handle" metaproperty="twitterSite"> <meta name="twitter:image:src" content="fallbackimage.jpg" metaproperty="image"> </head>

另一答案

使用Angular Universal,您可以为应用程序生成看起来像完整应用程序的登录页面,然后在其后面加载Angular应用程序。 Angular Universal生成纯HTML意味着服务器端的无javascript页面,并在不延迟的情况下将其提供给用户。因此,您可以处理任何爬虫,机器人和用户(已经具有低CPU和网络速度)。然后您可以通过链接/按钮将它们重定向到已经加载到其后面的实际角度应用程序。该解决方案由官方网站推荐。 https://prerender.io/documentation/install-middleware#asp-net

另一答案

爬虫(或机器人)旨在抓取网页的HTML内容,但由于异步数据获取的AJAX操作,这成为一个问题,因为它需要一些时间来呈现页面并在其上显示动态内容。同样,-More info about SEO and Angular Universal-也使用异步模型,这会为Google抓取工具带来问题。

一些开发人员使用真实数据创建基本的html页面,并在爬行时从服务器端提供这些页面。我们可以在AngularJS的服务端使用PhantomJS渲染相同的页面(因为Google在我们的网站网址中查找_escaped_fragment_,然后在#!之后获取所有内容并将其添加到#!查询参数中)。有关更多详细信息,请阅读此_escaped_fragment_

另一答案

爬虫不需要富有特色的漂亮风格的gui,他们只想看内容,所以你不需要给他们一个为人类构建的页面的快照。

我的解决方案:为爬虫提供爬虫想要的东西:

你必须考虑爬虫想要的东西,并且只给他那个。

提示不要乱背。只需使用相同的API添加一个服务器端的前端视图

另一答案

使用PushState和Precomposition

当前(2015)的方法是使用JavaScript pushState方法。

PushState更改顶部浏览器栏中的URL而不重新加载页面。假设您有一个包含标签的页面。选项卡隐藏和显示内容,并使用AJAX或简单地设置display:none和display:block来动态插入内容,以隐藏和显示正确的选项卡内容。

单击选项卡后,使用pushState更新地址栏中的URL。呈现页面时,使用地址栏中的值来确定要显示的选项卡。角度路由将自动为您执行此操作。

Precomposition

有两种方法可以访问PushState单页面应用程序(SPA)

  1. 通过PushState,用户单击PushState链接,内容为AJAX。
  2. 直接点击URL。

网站上的初始点击将涉及直接点击URL。随着PushState更新URL,后续命中将只是内容中的AJAX。

抓取工具从页面中获取链接,然后将它们添加到队列中以供稍后处理。这意味着对于爬虫来说,服务器上的每次点击都是直接命中,它们不会通过Pushstate导航。

预合成将初始有效负载捆绑到服务器的第一个响应中,可能作为JSON对象。这允许搜索引擎在不执行AJAX调用的情况下呈现页面。

有证据表明Google可能不会执行AJAX请求。更多相关信息:

this article

搜索引擎可以读取和执行JavaScript

谷歌已经能够解析JavaScript一段时间了,这就是他们最初开发Chrome的原因,它可以作为谷歌蜘蛛的全功能无头浏览器。如果链接具有有效的href属性,则可以为新URL编制索引。没有什么可做的了。

如果另外单击链接会触发pushState调用,则用户可以通过PushState导航该站点。

PushState URL的搜索引擎支持

目前,Google和Bing都支持PushState。

Google

这是Matt Cutts回应Paul Irish关于SEO的PushState的问题:

如何处理 Spring Boot、AngularJS 应用程序中的 CORS 错误?

登录时如何处理状态(Ionic、Firebase、AngularJS)?

browserify 如何处理循环依赖?

如何处理 $ctrl。在 AngularJS 中?

Typescript 和 AngularJS 1.5:如何处理导出类

Angularjs如何处理来自php(json)的二维数组