记开发个人图书收藏清单小程序开发(五)Web开发
决定先开发Web端试试。
新增Web应用:
选择ASP.NET Core Web Application,填写好Name和Location,然后点击OK。
注意红框标出来的,基于.NET Core 2.1版本。登录认证用了微软自带的Identity。Template选择Web Application,也即最新的Razor Pages试图引擎模式。
创建完毕,因为该Template自带的bootstrap还是3.3.7,所以从中文网站下载最新的bootstrap 4.x,同时还需要下载的是popper js插件(如果用到dropdown组件的话,不大明白为何新版Bootstrap不自带这个)。_Layout中的css和js引用也需要同步更新一下,还有就是Navbar菜单需要更新,因为3.x和4.x用的class样式完全不一样。
下面给出示例代码:
<nav class="navbar navbar-expand-lg navbar-light bg-light fixed-top">
<div class="container">
<a asp-page="/Index" class="navbar-brand">PTager Shelves</a>
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button> <div class="collapse navbar-collapse" id="navbarSupportedContent">
<ul class="navbar-nav mr-auto">
<li class="nav-item active">
<a class="nav-link" asp-page="/Index">Home</a>
</li>
<li class="nav-item">
<a class="nav-link" asp-page="/About">About</a>
</li>
<li class="nav-item">
<a class="nav-link" asp-page="/Contact">Contact</a>
</li>
</ul>
<partial name="_LoginPartial" />
</div>
</div>
</nav>
到此,Web项目基本改造完成了。
当然,前面说到我还是用PTager的现有的登录DB做登录功能,很简单,直接修改appsettings.json文件中的DB连接字符串就好了(如果没有也没事,直接用本地的空DB,注册的时候会提示如何自己创建DB)。
{
"ConnectionStrings": {
"DefaultConnection": "Server=.\\SQL2017;Database=PTager;Trusted_Connection=True;MultipleActiveResultSets=true"
},
"Logging": {
"LogLevel": {
"Default": "Warning"
}
},
"AllowedHosts": "*"
}
开始新增New Book功能。
先check豆瓣图书的api能不能正常调用。
在Pages文件夹下New Folder:Shelves,继续在Shelves文件夹New Item=>Razor Pages,Name直接改为:New。
为了接受豆瓣图书API获取的参数信息,先定义一个DoubanBookModel:
public class DoubanBookModel
{
public string title { get; set; }
public string subtitle { get; set; }
public IEnumerable<string> author { get; set; }
public IEnumerable<string> translator { get; set; }
public string isbn13 { get; set; }
public string isbn10 { get; set; }
public string author_intro { get; set; }
public string summary { get; set; }
public string publisher { get; set; }
public string binding { get; set; }
public string origin_title { get; set; }
public int pages { get; set; }
public string image { get; set; }
public string pubdate { get; set; }
public string catalog { get; set; }
public IEnumerable<TagItem> tags { get; set; }
public RatingItem rating { get; set; } public sealed class TagItem
{
public int count { get; set; }
public string name { get; set; }
public string title { get; set; }
}
public sealed class SeriesItem
{
public int id { get; set; }
public string title { get; set; }
}
public sealed class RatingItem
{
public int max { get; set; }
public int min { get; set; }
public int numRaters { get; set; }
public string average { get; set; }
}
}
/Pages/Sheves/New.cshtml:
@page
@model NewModel
@{
ViewData["Title"] = "New Book";
}
<nav aria-label="breadcrumb">
<ol class="breadcrumb">
<li class="breadcrumb-item"><a asp-page="/Index">Home</a></li>
<li class="breadcrumb-item"><a asp-page="/My Books/Index">My Books</a></li>
<li class="breadcrumb-item active" aria-current="page">New Book</li>
</ol>
</nav>
<form method="get">
<div class="input-group input-group-lg mb-3">
<div class="input-group-prepend">
<span class="input-group-text" id="basic-addon1">ISBN #</span>
</div>
<input name="isbn" class="form-control" autofocus autocomplete="off" placeholder="ISBN #">
<div class="input-group-append">
<button class="btn btn-secondary btn-lg" type="submit">Search</button>
</div>
</div>
</form>
<hr />
@if (Model.DoubanBook != null)
{
var item = Model.DoubanBook;
<div class="media">
@*<img class="align-self-start mr-3" src="@item.image" alt="Generic placeholder image">*@
<div class="media-body">
<h3 class="mt-0">@item.title<small class="ml-3">@item.subtitle</small></h3>
<p><strong>Origin Title: </strong> @item.origin_title</p>
<p><strong>Author: </strong> @string.Join("、", item.author)</p>
<p><strong>Translator: </strong> @string.Join("、", item.translator)</p>
<p>
<strong>Pubdate: </strong> @item.pubdate
<strong class="ml-3">Publisher: </strong> @item.publisher
<strong class="ml-3">Binding: </strong> @item.binding
<strong class="ml-3">Pages: </strong> @item.pages
</p>
<p>
<strong>ISBN: </strong> @item.isbn13
</p>
<p><strong class="mr-3">Author Intro:</strong> @item.author_intro</p>
<p><strong class="mr-3">Summary:</strong>@item.summary</p>
@foreach (var tag in item.tags)
{
<span class="badge badge-info">@tag.name</span>
}
</div>
</div>
<hr />
<form method="post">
<input type="hidden" asp-page="IsbnNbr">
<button class="btn btn-warning" type="submit">Add To My Books</button>
</form>
}
/Pages/Sheves/New.cshtml.cs:
public class NewModel : PageModel
{
[BindProperty]
public string IsbnNbr { get; set; }
public DoubanBookModel DoubanBook { get; set; } public async Task OnGetAsync(string isbn)
{
IsbnNbr = isbn?.Trim() ?? string.Empty;
if (validIsbnNbr(IsbnNbr))
{
DoubanBook = await getDoubanBook();
}
}
private async Task<DoubanBookModel> getDoubanBook()
{
var url = $"https://api.douban.com/v2/book/isbn/:{IsbnNbr}";
var result = await HttpGetAsync(url);
return JsonConvert.DeserializeObject<DoubanBookModel>(result);
}
public async Task<string> HttpGetAsync(string url, Encoding encoding = null)
{
using (var httpClient = new HttpClient())
{
return await httpClient.GetStringAsync(url);
}
} private bool validIsbnNbr(string isbn)
=> !string.IsNullOrEmpty(IsbnNbr) && (IsbnNbr.Length == || IsbnNbr.Length == );
}
好了,现在可以直接从豆瓣图书API获取到返回结果了,并且能展示在页面:
最新文章
- 安卓 android ListView 数据填充
- CodeForces 474B E(Contest #1)
- ecshop怎么添加配送方式
- 5.HBase In Action 第一章-HBase简介(1.1.3 HBase的兴起)
- CSS基础知识点(二)——居中
- 如何用C#代码查找某个路径下是否包含某个文件
- 转:socket编程在windows和linux下的区别
- HDU2015校赛 The Country List
- 网站卡死,照惯例运行.bat批量处理文件进行重启不起作用
- Android中的对话框AlertDialog使用技巧合集-转载
- 整理一批 国内外优秀设计团队 &; 设计相关网站
- java设计模式-----1、简单工厂模式
- fasthttp 文档手册
- SQL Server分页存储过程通用存储过程
- pycharm设置文件编码
- 查询的model里面 一般都要有一个要返回的model做属性 ;查询前要传入得参数,查询后返回的参数 都要集合在一个model中
- zabbix3.4.7常用监控项
- LeetCode--No.008 String to Integer (atoi)
- .net Core 依赖注入 Add********说明
- Netty入门(四)ByteBuf 字节级别的操作
热门文章
- 小程序本作用域下怎么调用全局js
- linux-ububtu64位安装docker,及基本命令
- React爬坑秘籍(一)——提升渲染性能
- Mysql 查询列名
- 带入gRPC:gRPC Streaming, Client and Server
- python&#39;s decorator&;wrapper
- java基础三 [深入多态,接口和多态](阅读Head First Java记录)
- testng的xml文件说明(TestNG DTD)
- react native 触摸Touchable***的区别(TouchableWithoutFeedback、TouchableOpacity、TouchableHighlight、TouchableNativeFeedback)
- PHP与Imagemagick