Android实战之Jsoup爬取简书网站首页详解

前言

我们都知道,个人开发者想要独立完成一个属于自己的App,数据来源就是一个不得不考虑的问题,那么我们App的数据通常是从哪些地方获取呢?主要是从以下三个地方获取的

  • 后台服务器提供的Api接口
  • 一些网站提供的Api接口。例如:聚合数据,干货集中营,玩Android开放Api等等还有很多,这里我只是抛砖引玉。
  • 通过抓包软件对个别App做抓包操作得到的Api接口
  • 通过爬虫获取各个网站的网页数据,在Android端主要使用的框架是Jsoup

我们今天要讲解的就是通过爬虫的这种方式,其它几种方式以后有空再进行讲解

什么是Jsoup框架

Jsoup 是一款Java 的HTML解析器,可直接解析某个URL地址、HTML文本内容。它提供了一套非常省力的API,可通过DOM,CSS以及类似于jQuery的操作方法来取出和操作数据。Jsoup中文文档

首先我们要先找到简书网站的首页

简书网站首页

我们要爬取的是简书首页的文章列表数据如下所示

Android实战之Jsoup爬取简书网站首页详解_第1张图片

通过F12快捷键或者点击右键的检查网页源代码可以找到文章列表所对应的源代码如下所示

Android实战之Jsoup爬取简书网站首页详解_第2张图片

然后我们就可以通过Jsoup框架获取html文档并一步步解析我们想要的元素数据封装到实体类中了

 //获取Html,得到document文件,设置超时时间为10秒,get请求
 document = Jsoup.connect("https://www.jianshu.com/")
 .timeout(10000)
 .get();
 
 //得到ul类名为:note-list的元素,ul代表无序列表
 Elements noteList = document.select("ul.note-list");

 //得到li标签所对应的元素
 Elements li = noteList.select("li");

//for each遍历li元素item里的所有元素并将数据封装到本地实体类中
  for (Element element : li) {
   //得到一个实体类
  SampleBookBean bean = new SampleBookBean();

 // 作者姓名
 bean.setAuthorName(element.select("a.nickname").text());
 Logger.d(element.select("a.nickname").text());

// 作者首页链接
bean.setAuthorLink(element.select("a.blue-link").attr("abs:href"));
Logger.d(element.select("a.blue-link").attr("abs:href"));

 // 主图
 bean.setPrimaryImg(element.select("img").attr("abs:src"));
Logger.d(element.select("img").attr("abs:src"));

 // 标题
bean.setTitle(element.select("a.title").text());
Logger.d(element.select("a.title").text());

// 标题链接
bean.setTitleLink(element.select("a.title").attr("abs:href"));
Logger.d(element.select("a.title").attr("abs:href"));

// 内容
bean.setContent(element.select("p.abstract").text());
Logger.d(element.select("p.abstract").text());

 // 专题链接
bean.setCollectionTagLink(element.select("a.nickname").attr("abs:href"));
Logger.d("链接数据"+element.select("a.nickname").attr("abs:href"));

bean.setLikeNum(element.select("span").text());
Logger.d("喜欢数"+element.select("span").text());

String[] text = element.select("div.meta").text().split(" ");
if (text[0].matches("[0-9]+")) {
          bean.setReadNum(text[0]);
          bean.setTalkNum(text[1]);
          bean.setLikeNum(text[2]);
          } else {
          bean.setCollectionTag(text[0]);
          bean.setReadNum(text[1]);
          bean.setTalkNum(text[2]);
          }
          sampleBookBeanList.add(bean);
          }

         runOnUiThread(new Runnable() {
          @Override
          public void run() {
          mAdapter.setNewData(sampleBookBeanList);
          swipeRefreshLayout.setRefreshing(false);
          }
        });

        Logger.d(sampleBookBeanList.get(0).toString());
       } catch (IOException e) {
          e.printStackTrace();
          Logger.d( e.getMessage());
                }
            }
        }).start();

最后在Android端用一个webView加载文章详情页数据,实现代码如下所示:

public class ShowActivity extends AppCompatActivity {

    private Toolbar toolbar;
    private WebView webView;
    private ProgressBar progressBar;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_show);

        String link = getIntent().getStringExtra("link");

        toolbar = (Toolbar) findViewById(R.id.tb_show_activity);
        webView = (WebView) findViewById(R.id.webview);
        progressBar = (ProgressBar) findViewById(R.id.progress_bar);

        initAppBar();

        //初始化WebView
        initWebView(link);

        //初始化webView相关设置
        initWebSettings();

        //对webview进行监听回调,WebViewClient主要处理各种通知、请求事件的
        initWebViewClient();

        //WebChromeClient主要辅助WebView处理Javascript的对话框、网站图标、网站title、加载进度等
        initWebChromeClient();
    }

    private void initWebView(String url) {
        webView.loadUrl(url);
    }

    private void initWebSettings() {
        WebSettings settings = webView.getSettings();
        //支持获取手势焦点
        webView.requestFocusFromTouch();
        //支持JS
        settings.setJavaScriptEnabled(true);
        //支持插件
        settings.setPluginState(WebSettings.PluginState.ON);
        //设置适应屏幕
        settings.setUseWideViewPort(true);
        settings.setLoadWithOverviewMode(true);
        //支持缩放
        settings.setSupportZoom(true);
        //隐藏原生得缩放控件
        settings.setDisplayZoomControls(false);
        //支持内容重新布局
        settings.setLayoutAlgorithm(WebSettings.LayoutAlgorithm.SINGLE_COLUMN);
        settings.supportMultipleWindows();
        settings.setSupportMultipleWindows(true);
        //设置缓存模式
        settings.setDomStorageEnabled(true);
        settings.setDatabaseEnabled(true);
        settings.setCacheMode(WebSettings.LOAD_DEFAULT);
        settings.setAppCacheEnabled(true);
        settings.setAppCachePath(webView.getContext().getCacheDir().getAbsolutePath());

        //设置可访问文件
        settings.setAllowFileAccess(true);
        //当webview调用requestFocus时为webview设置节点
        settings.setNeedInitialFocus(true);
        //支持自动加载图片
        if (Build.VERSION.SDK_INT >= 19){
            settings.setLoadsImagesAutomatically(true);
        } else {
            settings.setLoadsImagesAutomatically(false);
        }
        settings.setNeedInitialFocus(true);
        //设置编码格式
        settings.setDefaultTextEncodingName("UTF-8");
    }

    private void initWebViewClient() {
        webView.setWebViewClient(new WebViewClient(){
            @Override
            public void onPageStarted(WebView view, String url, Bitmap favicon) {
                super.onPageStarted(view, url, favicon);
                progressBar.setVisibility(View.VISIBLE);
            }

            @Override
            public void onPageFinished(WebView view, String url) {
                super.onPageFinished(view, url);
                progressBar.setVisibility(View.GONE);
            }

            @Override
            public boolean shouldOverrideUrlLoading(WebView view, WebResourceRequest request) {
                view.loadUrl(request.toString());
                return true;
            }

            @Override
            public void onReceivedError(WebView view, WebResourceRequest request, WebResourceError error) {
                super.onReceivedError(view, request, error);

            }
        });
    }

    private void initWebChromeClient() {
        webView.setWebChromeClient(new WebChromeClient(){
            private Bitmap mDefaultVideoPoster;//默认得视频展示图

            @Override
            public void onReceivedTitle(WebView view, final String title) {
                super.onReceivedTitle(view, title);
                if (toolbar != null){
                    toolbar.post(new Runnable() {
                        @Override
                        public void run() {
                            toolbar.setTitle(TextUtils.isEmpty(title) ? "加载中..." : title);
                        }
                    });
                }
            }

            @Override
            public Bitmap getDefaultVideoPoster() {
                if (mDefaultVideoPoster == null){
                    mDefaultVideoPoster = BitmapFactory.decodeResource(getResources(), R.mipmap.ic_launcher);
                    return mDefaultVideoPoster;
                }
                return super.getDefaultVideoPoster();
            }
        });
    }

    private void initAppBar() {
        toolbar.setTitle("载入中...");
        setSupportActionBar(toolbar);
        if(null!=getSupportActionBar())
        getSupportActionBar().setDisplayHomeAsUpEnabled(true);
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        if (item.getItemId() == android.R.id.home){
            finish();
        }
        return true;
    }
}


在App中的预览效果如下

Android实战之Jsoup爬取简书网站首页详解_第3张图片

你可能感兴趣的:(Android知识体系,Web前端知识体系)