生命不止,继续 go go go !!!
继续分享关于kataras/iris框架
i18n
i18n(其来源是英文单词 internationalization的首末字符i和n,18为中间的字符数)是“国际化”的简称。在资讯领域,国际化(i18n)指让产品(出版物,软件,硬件等)无需做大的改变就能够适应不同的语言和地区的需要。对程序来说,在不修改内部代码的情况下,能根据不同语言及地区显示相应的界面。 在全球化的时代,国际化尤为重要,因为产品的潜在用户可能来自世界的各个角落。通常与i18n相关的还有L10n(“本地化”的简称)。
新建文件夹locales,新建三个文件配置文件,分别对应中文、英文、希腊文:
locale_zh-CN.ini
hi = 您好,%s
locale_en-US.ini
hi = hello, %s
locale_el-GR.ini
hi = γεια, %s
main.go代码:
package main
import (
"github.com/kataras/iris"
"github.com/kataras/iris/context"
"github.com/kataras/iris/middleware/i18n"
)
func newApp() *iris.Application {
app := iris.New()
app.Use(i18n.New(i18n.Config{
Default: "en-US",
URLParameter: "lang",
Languages: map[string]string{
"en-US": "./locales/locale_en-US.ini",
"el-GR": "./locales/locale_el-GR.ini",
"zh-CN": "./locales/locale_zh-CN.ini"}}))
app.Get("/", func(ctx context.Context) {
hi := i18n.Translate(ctx, "hi", "iris")
language := ctx.Values().GetString(ctx.Application().ConfigurationReadOnly().GetTranslateLanguageContextKey())
ctx.Writef("From the language %s translated output: %s", language, hi)
})
return app
}
func main() {
app := newApp()
// go to http://localhost:8080/?lang=el-GR
// or http://localhost:8080
// or http://localhost:8080/?lang=zh-CN
app.Run(iris.Addr(":8080"))
}
浏览器输入:localhost:8080
由于我的PC是中文,所以显示:
From the language zh-CN translated output: 您好,iris
通过curl访问:
curl localhost:8080
结果:From the language en-US translated output: hello, iris
filelogger
主要是用于http log to file.
(不推荐使用)
main,.go
package main
import (
"os"
"time"
"github.com/kataras/iris"
"github.com/kataras/iris/context"
)
// get a filename based on the date, file logs works that way the most times
// but these are just a sugar.
func todayFilename() string {
today := time.Now().Format("2006-01-02")
return today + ".txt"
}
func newLogFile() *os.File {
filename := todayFilename()
// open an output file, this will append to the today's file if server restarted.
f, err := os.OpenFile(filename, os.O_CREATE|os.O_WRONLY|os.O_APPEND, 0666)
if err != nil {
panic(err)
}
return f
}
func main() {
f := newLogFile()
defer f.Close()
app := iris.New()
// attach the file as logger, remember, iris' app logger is just an io.Writer.
app.Logger().SetOutput(newLogFile())
app.Get("/", func(ctx context.Context) {
// for the sake of simplicity, in order see the logs at the ./_today_.txt
ctx.Application().Logger().Info("Request path: " + ctx.Path() + "\n")
ctx.Writef("hello")
})
if err := app.Run(iris.Addr(":8080"), iris.WithoutBanner); err != nil {
if err != iris.ErrServerClosed {
app.Logger().Warn("Shutdown with error: " + err.Error())
}
}
}
recaptcha
CMU 设计了一个名叫 reCAPTCHA 的强大系统,让他们的电脑去向人类求助。具体做法是:将 OCR 软件无法识别的文字扫描图传给世界各大网站,用以替换原来的验证码图片,这些网站的用户在正确识别出这些文字之后,其答案便会被传回CMU。所以 reCAPTCHA 本质上是一个披着验证码皮的分布式文字识别系统(OCR)。
reCAPTCHA 是利用 CAPTCHA(全自动区分计算机和人类的图灵测试) 的原理借助于人类大脑对难以识别的字符的辨别能力,进行对古旧书籍中难以被 OCR 识别的字符进行辨别的技术。也就是说,reCAPTCHA 不仅可以反 spam(垃圾内容),而且同时还可以帮助进行古籍的数字化工作(可以称为人工OCR)。只能说这个创意简直是绝了!所以即便由于 reCAPTCHA 是 Google 的产品在国内无法正常使用,但还是会应用到我们的这个 Blog 项目中,再通过应用反向代理的方式使之成为可行。
使用
在注册一个 Google 用户名后,进入到 reCAPTCHA 官网 并输入你的 blog 名(随意填写)和域名(只支持域名和子域名,现在我们暂时使用 localhost,等部署到线上之后也需要将新的域名填入),就会得到一个 Public Key,就可以把它用在你的 reCAPTCHA 插件上了,同时 reCAPTCHA 也支持多个站点。
这里使用iris为我们提供的recaptcha功能。
更推荐的方式是:https://github.com/dchest/captcha
main.go
package main
import (
"fmt"
"github.com/kataras/iris"
"github.com/kataras/iris/context"
"github.com/kataras/iris/middleware/recaptcha"
)
// publicDataSiteKey and secretKey and should be obtained by https://www.google.com/recaptcha.
const (
publicDataSiteKey = "6LfiVjcUAAAAAJyjCEGVyTpmFqlpOMGVIZpZPy6p"
secretKey = "6LfiVjcUAAAAAJ7wALWYNew2yx0qbT0WxRR-kYu9"
)
func main() {
app := iris.New()
r := recaptcha.New(secretKey)
app.Get("/comment", showRecaptchaForm)
// pass the middleware before the main handler or use the `recaptcha.SiteVerify`.
app.Post("/comment", r, postComment)
app.Run(iris.Addr(":8080"))
}
var htmlForm = `<form action="/comment" method="POST">
<script src="https://www.google.com/recaptcha/api.js"></script>
<div class="g-recaptcha" data-sitekey="%s"></div>
<input type="submit" name="button" value="Verify">
</form>`
func showRecaptchaForm(ctx context.Context) {
contents := fmt.Sprintf(htmlForm, publicDataSiteKey)
ctx.HTML(contents)
}
func postComment(ctx context.Context) {
// [...]
ctx.JSON(context.Map{"success": true})
}
// 20171106141744
// http://localhost:8080/comment
{
"success": true
}