服务器上部署https,免费又好用的https证书

随着苹果发布声明接口https化,再加上微信小程序的接口必须使用https,可是服务器上部署https就需要一笔小小的费用,在天朝掏钱的事是没人干的,都在找寻免费的服务,虽然挺折腾,但是难不住天朝的程序员。特别是为了测试微信小程序,实在是没必要购买ssl证书,只好寻求免费的服务。

StartSSL(官网:https://www.startssl.com/),提供免费的ssl证书申请,16年的时候按照网上的教程申请过一个免费的证书,用着还不错,17年的时候想为相同域名下的另一个二级域名申请证书的时候,提示系统正在升级,跳转到另一个主站,申请之后一直是Pending Issued(待签发)状态,也没有原因提醒,一直没搞懂神马情况,只好另寻办法。

Let’s Encrypt,免费的,开放的证书签发服务,之前也看到过,虽然只有90天的有效期,但是如果要安装 Let’s Encrypt 凭证,必须要熟悉 Unix 指令,才能够在远端主机下指令来取得凭证(不是很难,却需要一些时间)。自从发现了有开发者推出一款名为 SSL For Free 线上工具,让你从网站上取得免费 SSL 凭证,当然这是连接 Let’s Encrypt 的凭证签发功能,不过无须自己到主机输入安装指令,即可透过网页介面来取得凭证的相关档案(包括私密金钥、CA bundle 和凭证 crt 档),再从控制台 SSL 功能将凭证安装进去就能使用。

网站名称:SSL For Free
网站链接:https://www.sslforfree.com/

1,进入网站之后,直接在上方填入你要申请 Let’s Encrypt 凭证的网域名称,可以用空白来分隔不同的网址,例如「subdomain.domain.com domain.com other.com」,填入后点选右边的「Create Free SSL Certificate」继续。
2,为了确定这个网域名称使你所有,会有三种验证方式,如果你的网站本身开启 FTP 功能的话,可使用「Automatic FTP Verification」来输入相关资讯完成验证;还有一种就是DNS验证;我使用的是手动的验证方式,必须自己下载档案,依照说明上传到主机。

3,点选后,点选下方的「Manually Verify Domain」继续。
4,点选网站上提供的档案下载链接,依照说明建立两层资料夹,将档案放进去即可。记得结束前先通过以下两个链接来看看能否正常读取档案,如果不行,代表你的路径可能错误,重新检查一次吧!总之要让两个链接都能正常开启。由于使用的是windows主机,并且使用的IIS7,操作稍微麻烦一些,如果没有站点,需要先建一个站点,验证支持http或者https,在站点根目录创建.well-known文件夹,由于是特殊文件夹,直接创建肯定是创建不上,需要在文件名后再跟一个小圆点,既创建一个.well-known.【再windows下看到就是.well-known】,在它下面再创建一个acme-challenge文件夹,将下载下来的文件放到里面。由于下载下来的文件是无后缀的文件,需要在IIS上设置一下,支持无后缀的文件访问。打开IIS7,点击相应的站点,在功能视图,点击MIME类型,添加一个文件扩展为.*,mimeType类型为text/plain,这样就可以文本的方式访问无后缀的文件了。确保文件可以访问后
5,再点选最下方的「Download SSL Certificate」,通过验证后,SSL For Free 就会开始为你产生 SSL 凭证。
6,当凭证产生后,你就能在最终的结果页面看到这些资讯。不过在此之前,我会建议你先找到如下面截图标示出来的「Get Notified of Expiration」栏位,设定一组 Email 和密码,即可在凭证过期前取得通知,以免错过延长(renew)时间。从网页最下方点选「Download All SSL Certificate Files」就能打包这些档案,解压缩后可以取得一个私密金钥(Privacy Key)、CA_bundle.crt 和 certificate.crt 三个档案,返回你的主机控制台,即可将凭证安装进去囉!
7,由于是windows的IIS,直接下载下来的文件还无法部署到IIS7上,需要使用openssl将下载下来的文件转换成pfx的文件才可以导入到IIS的证书里.openssl使用的是Openssl-windows-0.9.8k命令行工具,在cmd里执行:
openssl pkcs12 -export -out domin.pfx -inkey private.key -in certificate.crt 会提示输入导入时的密码,导入证书的时候有用。生成pfx后可以导入到IIS里。参考网址:http://stackoverflow.com/questions/6307886/how-to-create-pfx-file-from-certificate-and-private-key/17284371#17284371
支持https已经设置完毕。

参考网站:http://www.chinaz.com/web/2016/0216/504896.shtml

注:windows服务器上默认是不支持TLS 1.2,要想服务器支持TLS 1.2,需要修改一下注册表,【例如苹果就要求必须为TLS 1.2】,禁用SSL3.0,启用TLS1.2如下:
注册表路径:HKLM SYSTEM\CurrentControlSet\Control\SecurityProviders\SCHANNEL\Protocols
右键->新建->项->新建TLS 1.1,TLS 1.2
TLS 1.1和TLS 1.2 右键->新建->项->新建Server, Client
在新建的Server和Client中都新建如下的项(DWORD 32位值), 总共4个
DisabledByDefault [Value = 0]
Enabled [Value = 1]

禁用老SSL配置
SSL 2.0,SSL 3.0项里的Client,Server项:
DisabledByDefault [Value = 0]
Enabled [Value = 0]
需要重启服务器

测试服务器ssl信息的网站:https://www.ssllabs.com/ssltest/
参考网站:http://www.chinaz.com/web/2016/0216/504896.shtml

发表在 开源, 服务器 | 标签为 , | 评论关闭

Windows Server2008 R2服务器IIS7站点突然爆出此实现不是 Windows 平台 FIPS 验证的加密算法的一部分的解决方法

有一台Windows Server 2008 R2服务器由于内存问题导致服务器蓝屏并不断重启,之后引起了一系列问题,特别是爆出了此实现不是Windows平台FIPS验证加密算法的一部分,前所未闻的问题犹如泰山压顶,迅速通过度娘,Google查找问题根源。查了数十个小时,可以分为两种,一种是组策略,一种是修改注册表。
1,开始,运行,输入 gpedit.msc打开组策略,左侧列表中找到 计算机配置 – Windows设置 – 安全设置 – 本地策略 – 安全选项,并在右侧找到“系统加密:将FIPS兼容算法用于加密、哈希和签名” 双击上述策略,在弹出的选项中,将状态改为已禁用。【系统本身已是禁用状态】
2更改注册表,开始,运行,输入regedit打开注册表,HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Lsa\FipsAlgorithmPolicy,将Enabled的值改为0  【值本身就为0】2   HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet001\Control\Lsa\FipsAlgorithmPolicy,将Enabled的值改为0  【值本身就为0】

当然还有一种是说在web.config文件里增加一行<runtime><enforceFIPSPolicy enabled=”false” /> </runtime>试了试还是不行。
搜便所有互联网,基本上都是上面的解决访问,时间一分一秒的过去了,还是一筹莫展,不能这样就重做系统吧!那么多站点部署也不是那么容易的。既然是程序报错,修改程序总可以吧!
1 System.InvalidOperationException: This implementation is not part of the Windows Platform FIPS validated cryptographic algorithms

首先碰到一个难题,就是md5加密这块,md5不可用,所有账号都是通过md5加密的,不可能换新的加密方式,既然系统的md5加密不可用,只好去网上搜搜C#写的md5加密类,还好找到了一个互联网大牛写的md5加密类,试了试还行,对字符等加密和原有的加密出来的一样。唯一的缺点是不支持中文,还好系统密码都限制了不能使用中文,满足条件,就将密码这块统一更换成了改md5加密方式。
2,针对缓存碰到的一个问题。由于硬盘比较廉价,站点使用了大量的文件缓存。在处理缓存子文件夹和缓存文件名的时候使用了md5对字符串加密,由于担心字符串含有中文,就无法使用上面的md5加密类,搜索之后发现了sha1加密方式,虽然比md5慢一点,但是完全符合唯一性。接下来就将所有与密码无关的md5加密全部换成了下方的sha1加密方式。

 public static string SHA1(string input)
        {
            using (System.Security.Cryptography.SHA1CryptoServiceProvider provider =
              new System.Security.Cryptography.SHA1CryptoServiceProvider()){
                      return BitConverter.ToString(
                               provider.ComputeHash(Encoding.UTF8.GetBytes(input))
                                                 ).Replace("-", "").ToLower();
            }
       }

3此实现不是 Windows 平台 FIPS 验证的加密算法的一部分

由于Net 2.0的站点都报这个错误,还以为也是与安全性有关,找了半天,最后新建了一个以aspx结尾的空文件,居然也报错,无计可施的时候,将该站点进程池切换到4.0下面,居然运行正常了,一直不清楚什么原理。不过切换到4.0之后,表单提交页面对ValidateRequest=”false”这个不起作用,如果表单包含html代码一样会报错,需要在web.config 增加<httpRuntime  requestValidationMode=”2.0″ />
至此站点基本恢复正常。

发表在 Net, 服务器 | 标签为 , | 评论关闭

IIS7静态资源站点部署方案_加快呈现速度的方法

在IIS7下,有时我们需要对网站引用的静态资源如小图,css,js等单独配置一个站点,供其它站点使用。掌握一些部署技巧,将会加快加载速度。
配置静态资源站的时候,应用程序池的最好选择无托管代码,集成模式。应用程序池的设置如下图:

还需要在站点根目录下放置一个web.config,移除多余的模块即可。

<?xml
version="1.0" encoding="utf-8"?>
<!--
  For more information on how to configure your ASP.NET application, please visit

http://go.microsoft.com/fwlink/?LinkId=152368

  -->
<configuration>
  <system.webServer>
    <modules>
      <remove name="OutputCache"/>
      <remove name="Session"/>
      <remove name="WindowsAuthentication"/>
      <remove name="FormsAuthentication"/>
      <remove name="PassportAuthentication"/>
      <remove name="RoleManager"/>
      <remove name="UrlAuthorization"/>
      <remove name="FileAuthorization"/>
      <remove name="AnonymousIdentification"/>
      <remove name="Profile"/>
      <remove name="ErrorHandlerModule"/>
      <remove name="ServiceModel"/>
      <remove name="UrlRoutingModule-4.0"/>
      <remove name="ScriptModule-4.0"/>
    </modules>
  </system.webServer>
</configuration>


有时我们的网站会将详细页生成静态页面(html,shtml),可以单独对生成的详细页面进行设置。在站点下创建应用程序,指向生成的静态页面,应用程序池选择无托管代码的集成模式的应用程序池.并将
上面的web.config放在应用程序的静态页面根目录。创建的时候最好创建应用程序,创建虚拟目录,在虚拟目录里放置web.config移除多余的模块将不会生效。

我们发布的网站也可以进行简单的优化,大部分网站很少会用到全部的模块,例如不常用的模块:Session、Profile等,也可以在网站的web.config相应的配置节移除掉这些用不到的模块来加快响应速度。

发表在 Net, 服务器 | 评论关闭

windows下npm无法安装任何包的完美解决办法

最近刚刚安装了node,在试用npm安装包的时候一直报:“npm ERR! code ECONNRESET”,怎么都不行,最后找到了一个简单的解决方法。找到node的安装目录下的node_modules\npm文件夹里找到文件npmrc,增加如下一下:

registry = http://registry.cnpmjs.org

完美解决,注:由于最新版的node已经安装了npm模块,安装完node后并不需要单独安装npm模块了。

发表在 Javascript | 评论关闭

高效的上一页下一页分页实现思路

在进行开发的时候,最常用的功能是分页,分页的实现很简单,方法也很多,有使用存储过程实现的,也有人使用row_number函数通过sql语句直接实现分页的,这些方法开发起来简单又高效。可是随着数据量一天天增大,慢慢就可以感觉到加载越来越缓慢。罪魁祸首是由于所有分页原理都使用了select count(*)聚合函数获取总记录数,用来计算总页数。对于需要显示页码的分页形式,目前没有想到很好的实现思路。不过对于只有上一页和下一页这种的分页形式,目前发现了一个更好的实现思路,具体实现如下:

创建测试用的表,并填充数据:


CREATE TABLE sysUser
(
   id INT IDENTITY(1,1) PRIMARY KEY,
   name NVARCHAR(50),
   age INT
)

DECLARE @i INT
SET @i=0
WHILE @i<1000
BEGIN
    SET @i=@i+1
    INSERT INTO dbo.sysUser
            ( name, age )
    VALUES  ( N'User'+LTRIM(STR(@i)), -- name - nvarchar(50)
              32  -- age - int
              )
END

创建一个实体类型User:


public class User
    {
        public int Id { get; set; }
        public string Name { get; set; }
        public int Age { get; set; }
    }

/// <summary>
        /// 为了演示写的一个简单的调取函数
        /// </summary>
        /// <param name="sql">();
         public List<User> Query(string sql)
          {
            List<User> _list=List<User>();
            using (SqlConnection conn = new SqlConnection(数据库连接字符串))
            {
                conn.Open();
                using (SqlCommand cmd = new SqlCommand(sql, conn))
                {
                    IDataReader dr = cmd.ExecuteReader(CommandBehavior.CloseConnection);
                    while (dr.Read())
                    {
                        _list.Add(new User {  Id=dr.GetInt32(0), Name=dr.GetString(1),Age=dr.GetInt32(2)});
                    }
                    dr.Close();
                    dr.Dispose();
                }
            }
            return _list;
        }

/// <summary>
        /// 返回要显示的数据
        /// </summary>
        /// <param name="strwhere">查询条件,可为空</param>
        /// <param name="orderby">排序条件,可为空</param>
        /// <param name="page">当前页数</param>
        /// <param name="pagesize">每天显示多少条</param>
        /// <param name="hasNextPage">有些站前台最多显示多少页的数据,
///例如有些站前台最多显示100页的数据,可以传递()=>{return page<100;},要想显示所有页的数据,可以传递()=>{return true;}</param>
        /// <param name="nextpage">返回参数,大于零,列表页会显示下一页,值为零,列表页不显示下一页</param>
        /// <returns></returns>
        public List<User> GetUserList(
string strwhere, string orderby, int page, int pagesize, Func<bool> hasNextPage, out int nextpage)
        {
            string sqlorder="id desc";
            string sqlwhere=" 1=1";
            if (!string.IsNullOrEmpty(orderby)) sqlorder = orderby;
            if (!string.IsNullOrEmpty(strwhere)) sqlwhere = sqlwhere + strwhere;
            int startnum = (page - 1) * pagesize + 1;    //开始行和之前的计算方式没有变化
             //主要变化是计算结束行,结束行每次要多获取一条,目的只是为了判断下一页是否有数据,多的这一条数据并不显示在页面上
            int endnum = page * pagesize + 1;
            string sql = string.Format(
"with temp as (select id,name,age,ROW_NUMBER() over(order by {0}) as pn from sysUser where {1})
select * from temp where pn between {2} and {3}"
, sqlorder, sqlwhere, startnum, endnum);

            List<User> _list = Query(sql);
            nextpage = 0;
            if (_list.Count == pagesize + 1)
            {
                if (hasNextPage())
                {
                    nextpage = page + 1;
                }
                else
                {
                    nextpage = 0;
                }
                _list.RemoveAt(_list.Count - 1);
            }
            return _list;
        }

使用的时候只需通过如下方式进行调取:


int nextpage = 0;      //页面可以该变量来判断是否显示下一页,大于零显示下一页。
List<User> list = GetUserList("", "", page, 2, () => {return page < 48; },out nextpage);  //page为传递过来的当前第几页.

以上仅为上一页,下一页分页的一个具体实现,在数据量大的情况下,业务有没有特殊需求,只需要提供上一页下一页的情况下可以参考此类实现,减轻数据库压力。

发表在 Net | 评论关闭