Inkscape 是一个流行的、功能齐全、自由而开源的矢量图形编辑器，它已经在 Fedora 官方仓库中。它特别适合创作 SVG 格式的矢量图形。Inkscape 非常适于创建和操作图片和插图，以及创建图表和用户界面设计。使用 inkscape 创建的风车景色的插图其官方网站的截图页上有一些很好的例子，说明 Inkscape 可以做些什么。 Fedora 杂志 Fedora Magazine 上的大多数精选图片也是使用 Inkscape 创建的，包括最近的精选图片：Fedora 杂志最近使用 Inkscape 创建的精选图片在 Fedora 上安装 InkscapeInkscape 已经在 Fedora 官方仓库中了，因此可以非常简单地在 Fedora Workstation 上使用 Software 这个应用来安装它：另外，如果你习惯用命令行，你可以使用 dnf 命令来安装：sudo dnf install inkscape （开始）深入 Inkscape当第一次打开程序时，你会看到一个空白页面，并且有一组不同的工具栏。对于初学者，最重要的三个工具栏是：Toolbar、Tools Control Bar、 Colour Palette：Toolbar提供了创建绘图的所有基本工具，包括以下工具：矩形工具：用于绘制矩形和正方形星形/多边形（形状）工具圆形工具：用于绘制椭圆和圆文本工具：用于添加标签和其他文本路径工具：用于创建或编辑更复杂或自定义的形状选择工具：用于选择图形中的对象Colour Palette 提供了一种设置当前选定对象的颜色的快速方式。 Tools Control Bar 提供了工具栏中当前选定工具的所有设置。每次选择新工具时，Tools Control Bar 会变成该工具的相应设置：绘图接下来，让我们使用 Inkscape 绘制一个星星。 首先，从 Toolbar 中选择星形工具，然后在主绘图区域上单击并拖动。你可能会注意到你画的星星看起来很像一个三角形。要更改它，请使用 Tools Control Bar 中的 Corners 选项，再添加几个点。 最后，当你完成后，在星星仍被选中的状态下，从 Palette（调色板）中选择一种颜色来改变星星的颜色：接下来，可以在 Toolbar 中实验一些其他形状工具，如矩形工具，螺旋工具和圆形工具。通过不同的设置，每个工具都可以创建一些独特的图形。在绘图中选择并移动对象现在你有一堆图形了，你可以使用 Select 工具来移动它们。要使用 Select 工具，首先从工具栏中选择它，然后单击要操作的形状，接着将图形拖动到您想要的位置。选择形状后，你还可以使用尺寸句柄调整图形大小。此外，如果你单击所选的图形，尺寸句柄将转变为旋转模式，并允许你旋转图形：Inkscape是一个很棒的软件，它还包含了更多的工具和功能。在本系列的下一篇文章中，我们将介绍更多可用来创建插图和文档的功能和选项。作者简介：Ryan 是一名 Fedora 设计师。他使用 Fedora Workstation 作为他的主要桌面，还有来自 Libre Graphics 世界的最好的工具，尤其是矢量图形编辑器 Inkscape。via: https://fedoramagazine.org/getting-started-inkscape-fedora/作者：Ryan Lerch 译者：geekpi 校对：jasminepeng本文由 LCTT 原创编译，Linux中国 荣誉推出
忘记技术债务 —— 教你如何创造技术财富
电视里正播放着《老屋》节目，Andrea Goulet 和她的商业合作伙伴正悠闲地坐在客厅里，商讨着他们的战略计划。那正是大家思想的火花碰撞出创新事物的时刻。他们正在寻求一种能够实现自身价值的方式 —— 为其它公司清理 遗留代码 legacy code 及科技债务。他们此刻的情景，像极了电视里的场景。（LCTT 译注：《老屋》电视节目提供专业的家装、家庭改建、重新装饰、创意等等信息，与软件的改造有异曲同工之处）。“我们意识到我们现在做的工作不仅仅是清理遗留代码，实际上我们是在用重建老屋的方式来重构软件，让系统运行更持久、更稳定、更高效，”Goulet 说。“这让我开始思考公司如何花钱来改善他们的代码，以便让他们的系统运行更高效。就好比为了让屋子变得更有价值，你不得不使用一个全新的屋顶。这并不吸引人，但却是至关重要的，然而很多人都搞错了。“如今，她是 Corgibytes 公司的 CEO —— 这是一家提高软件现代化和进行系统重构方面的咨询公司。她曾经见过各种各样糟糕的系统、遗留代码，以及严重的科技债务事件。Goulet 认为创业公司需要转变思维模式，不是偿还债务，而是创造科技财富，不是要铲除旧代码，而是要逐步修复代码。她解释了这种新的方法，以及如何完成这些看似不可能完成的事情 —— 实际上是聘用优秀的工程师来完成这些工作。反思遗留代码关于遗留代码最常见的定义是由 Michael Feathers 在他的著作 《高效利用遗留代码》 Working Effectively with Legacy Code 一书中提出：遗留代码就是没有被测试所覆盖的代码。这个定义比大多数人所认为的 —— 遗留代码仅指那些古老、陈旧的系统这个说法要妥当得多。但是 Goulet 认为这两种定义都不够明确。“遗留代码与软件的年头儿毫无关系。一个两年的应用程序，其代码可能已经进入遗留状态了，”她说。“关键要看软件质量提高的难易程度。”这意味着写得不够清楚、缺少解释说明的代码，是没有包含任何关于代码构思和决策制定的流程的成果。单元测试就是这样的一种成果，但它并没有包括了写那部分代码的原因以及逻辑推理相关的所有文档。如果想要提升代码，但没办法搞清楚原开发者的意图 —— 那些代码就属于遗留代码了。遗留代码不是技术问题，而是沟通上的问题。如果你像 Goulet 所说的那样迷失在遗留代码里，你会发现每一次的沟通交流过程都会变得像那条 康威定律 Conway’s Law 所描述的一样。Goulet 说：“这个定律认为你的代码能反映出整个公司的组织沟通结构，如果想修复公司的遗留代码，而没有一个好的组织沟通方式是不可能完成的。那是很多人都没注意到的一个重要环节。”Goulet 和她的团队成员更像是考古学家一样来研究遗留系统项目。他们根据前开发者写的代码构件相关的线索来推断出他们的思想意图。然后再根据这些构件之间的关系来做出新的决策。代码构件最重要的什么呢？良好的代码结构、清晰的思想意图、整洁的代码。例如，如果使用通用的名称如 “foo” 或 “bar” 来命名一个变量，半年后再返回来看这段代码时，根本就看不出这个变量的用途是什么。如果代码读起来很困难，可以使用源代码控制系统，这是一个非常有用的工具，因为它可以提供代码的历史修改信息，并允许软件开发者写明他们作出本次修改的原因。Goulet 说：“我一个朋友认为提交代码时附带的信息，每一个概要部分的内容应该有半条推文那么长（几十个字），如需要的话，代码的描述信息应该有一篇博客那么长。你得用这个方式来为你修改的代码写一个合理的说明。这不会浪费太多额外的时间，并且能给后期的项目开发者提供非常多的有用信息，但是让人惊讶的是很少有人会这么做。我们经常能看到一些开发人员在被一段代码激怒之后，要用 git blame 扒代码库找出这些垃圾是谁干的，结果最后发现是他们自己干的。”使用自动化测试对于理解程序的流程非常有用。Goulet 解释道：“很多人都比较认可 Michael Feathers 提出的关于遗留代码的定义。测试套件对于理解开发者的意图来说是非常有用的工具，尤其当用来与 行为驱动开发模式 Behavior Driven Development 相结合时，比如编写测试场景。”理由很简单，如果你想将遗留代码限制在一定程度下，注意到这些细节将使代码更易于理解，便于在以后也能工作。编写并运行一个代码单元，接受、认可，并且集成测试。写清楚注释的内容，方便以后你自己或是别人来理解你写的代码。尽管如此，由于很多已知的和不可意料的原因，遗留代码仍然会出现。在创业公司刚成立初期，公司经常会急于推出很多新的功能。开发人员在巨大的交付压力下，测试常常半途而废。Corgibytes 团队就遇到过好多公司很多年都懒得对系统做详细的测试了。确实如此，当你急于开发出系统原型的时候，强制性地去做太多的测试也许意义不大。但是，一旦产品开发完成并投入使用后，你就需要投入时间精力来维护及完善系统了。Goulet 说：“很多人说，‘别在维护上费心思，重要的是功能！’ 如果真这样，当系统规模到一定程序的时候，就很难再扩展了。同时也就失去市场竞争力了。”最后才明白过来，原来热力学第二定律对代码也同样适用：你所面临的一切将向熵增的方向发展。你需要与混乱无序的技术债务进行一场无休无止的战斗。随着时间的推移，遗留代码也逐渐变成一种债务。她说：“我们再次拿家来做比喻。你必须坚持每天收拾餐具、打扫卫生、倒垃圾。如果你不这么做，情况将来越来越糟糕，直到有一天你不得不向 HazMat 团队求助。”（LCTT 译注：HazMat 团队，危害物质专队)就跟这种情况一样，Corgibytes 团队接到很多公司 CEO 的求助电话，比如 Features 公司的 CEO 在电话里抱怨道：“现在我们公司的开发团队工作效率太低了，三年前只需要两个星期就完成的工作，现在却要花费12个星期。”技术债务往往反映出公司运作上的问题。很多公司的 CTO 明知会发生技术债务的问题，但是他们很难说服其它同事相信花钱来修复那些已经存在的问题是值得的。这看起来像是在走回头路，很乏味，也不是新的产品。有些公司直到系统已经严重影响了日常工作效率时，才着手去处理这些技术债务方面的问题，那时付出的代价就太高了。忘记债务，创造技术财富如果你想把 重构技术债务 reframe your technical debt — 敏捷开发讲师 Declan Whelan 最近造出的一个术语 — 作为一个积累技术财富的机会，你很可能要先说服你们公司的 CEO、投资者和其它的股东接受并为之共同努力。“我们没必要把技术债务想像得很可怕。当产品处于开发设计初期，技术债务反而变得非常有用，”Goulet 说。“当你解决一些系统遗留的技术问题时，你会充满成就感。例如，当你在自己家里安装新窗户时，你确实会花费一笔不少的钱，但是之后你每个月就可以节省 100 美元的电费。程序代码亦是如此。虽然暂时没有提高工作效率，但随时时间推移将提高生产力。”一旦你意识到项目团队工作不再富有成效时，就需要确认下是哪些技术债务在拖后腿了。“我跟很多不惜一切代价招募英才的初创公司交流过，他们高薪聘请一些工程师来只为了完成更多的工作。”她说。“与此相反，他们应该找出如何让原有的每个工程师能更高效率工作的方法。你需要去解决什么样的技术债务以增加额外的生产率？”如果你改变自己的观点并且专注于创造技术财富，你将会看到产能过剩的现象，然后重新把多余的产能投入到修复更多的技术债务和遗留代码的良性循环中。你们的产品将会走得更远，发展得更好。别把你们公司的软件当作一个项目来看。从现在起，把它想象成一栋自己要长久居住的房子。“这是一个极其重要的思想观念的转变，”Goulet 说。“这将带你走出短浅的思维模式，并让你比之前更加关注产品的维护工作。”这就像对一栋房子，要实现其现代化及维护的方式有两种：小动作，表面上的更改（“我买了一块新的小地毯！”）和大改造，需要很多年才能偿还所有债务（“我想我们应替换掉所有的管道...”)。你必须考虑好两者，才能让你们已有的产品和整个团队顺利地运作起来。这还需要提前预算好 —— 否则那些较大的花销将会是硬伤。定期维护是最基本的预期费用。让人震惊的是，很多公司都没把维护当成商务成本预算进来。这就是 Goulet 提出“ 软件重构 software remodeling ”这个术语的原因。当你房子里的一些东西损坏的时候，你并不是铲除整个房子，从头开始重建。同样的，当你们公司出现老的、损坏的代码时，重写代码通常不是最明智的选择。下面是 Corgibytes 公司在重构客户代码用到的一些方法：把大型的应用系统分解成轻量级的更易于维护的微服务。让功能模块彼此解耦以便于扩展。更新形象和提升用户前端界面体验。集合自动化测试来检查代码可用性。代码库可以让重构或者修改更易于操作。系统重构也进入到 DevOps 领域。比如，Corgibytes 公司经常推荐新客户使用 Docker，以便简单快速的部署新的开发环境。当你们团队有 30 个工程师的时候，把初始化配置时间从 10 小时减少到 10 分钟对完成更多的工作很有帮助。系统重构不仅仅是应用于软件开发本身，也包括如何进行系统重构。如果你知道做些什么能让你们的代码管理起来更容易更高效，就应该把这它们写入到每年或季度的项目规划中。别指望它们会自动呈现出来。但是也别给自己太大的压力来马上实施它们。Goulets 看到很多公司从一开始就致力于 100% 测试覆盖率而陷入困境。具体来说，每个公司都应该把以下三种类型的重构工作规划到项目建设中来：自动测试持续交付文化提升咱们来深入的了解下每一项内容。自动测试“有一位客户即将进行第二轮融资，但是他们没办法在短期内招聘到足够的人才。我们帮助他们引进了一种自动化测试框架，这让他们的团队在 3 个月的时间内工作效率翻了一倍，”Goulets 说。“这样他们就可以在他们的投资人面前自豪的说，‘我们一个精英团队完成的任务比两个普通的团队要多。’”自动化测试从根本上来讲就是单个测试的组合，就是可以再次检查某一行代码的单元测试。可以使用集成测试来确保系统的不同部分都正常运行。还可以使用验收性测试来检验系统的功能特性是否跟你想像的一样。当你把这些测试写成测试脚本后，你只需要简单地用鼠标点一下按钮就可以让系统自行检验了，而不用手工的去梳理并检查每一项功能。在产品市场尚未打开之前就来制定自动化测试机制有些言之过早。但是一旦你有一款感到满意，并且客户也很依赖的产品，就应该把这件事付诸实施了。持续交付这是与自动化交付相关的工作，过去是需要人工完成。目的是当系统部分修改完成时可以迅速进行部署，并且短期内得到反馈。这使公司在其它竞争对手面前有很大的优势，尤其是在客户服务行业。“比如说你每次部署系统时环境都很复杂。熵值无法有效控制，”Goulets 说。“我们曾经见过花 12 个小时甚至更多的时间来部署一个很大的集群环境。在这种情况下，你不会愿意频繁部署了。因为太折腾人了，你还会推迟系统功能上线的时间。这样，你将落后于其它公司并失去竞争力。”在持续性改进的过程中常见的其它自动化任务包括：在提交完成之后检查构建中断部分。在出现故障时进行回滚操作。自动化审查代码的质量。根据需求增加或减少服务器硬件资源。让开发、测试及生产环境配置简单易懂。举一个简单的例子，比如说一个客户提交了一个系统 Bug 报告。开发团队越高效解决并修复那个 Bug 越好。对于开发人员来说，修复 Bug 的挑战根本不是个事儿，这本来也是他们的强项，主要是系统设置上不够完善导致他们浪费太多的时间去处理 bug 以外的其它问题。使用持续改进的方式时，你要严肃地决定决定哪些工作应该让机器去做，哪些交给研发去完成更好。如果机器更擅长，那就使其自动化完成。这样也能让研发愉快地去解决其它有挑战性的问题。同时客户也会很高兴地看到他们报怨的问题被快速处理了。你的待修复的未完成任务数减少了，之后你就可以把更多的时间投入到运用新的方法来提高产品的质量上了。这是创造科技财富的一种转变。因为开发人员可以修复 bug 后立即发布新代码，这样他们就有时间和精力做更多事。“你必须时刻问自己，‘我应该如何为我们的客户改善产品功能？如何做得更好？如何让产品运行更高效？’不过还要不止于此。”Goulets 说。“一旦你回答完这些问题后，你就得询问下自己，如何自动去完成那些需要改善的功能。”文化提升Corgibytes 公司每天都会看到同样的问题：一家创业公司建立了一个对开发团队毫无推动的文化环境。公司 CEO 抱着双臂思考着为什么这样的环境对员工没多少改变。然而事实却是公司的企业文化对工作并不利。为了激励工程师，你必须全面地了解他们的工作环境。为了证明这一点，Goulet 引用了作者 Robert Henry 说过的一段话：目的不是创造艺术，而是在最美妙的状态下让艺术应运而生。“你们也要开始这样思考一下你们的软件，”她说。“你们的企业文件就类似那个状态。你们的目标就是创造一个让艺术品应运而生的环境，这件艺术品就是你们公司的代码、一流的售后服务、充满幸福感的开发者、良好的市场预期、盈利能力等等。这些都息息相关。”优先考虑解决公司的技术债务和遗留代码也是一种文化。那是真正为开发团队清除障碍，以制造影响的方法。同时，这也会让你将来有更多的时间精力去完成更重要的工作。如果你不从根本上改变固有的企业文化环境，你就不可能重构公司产品。改变对产品维护及现代化的投资的态度是开始实施变革的第一步，最理想情况是从公司的 CEO 开始自顶向下转变。以下是 Goulet 关于建立那种流态文化方面提出的建议：反对公司嘉奖那些加班到深夜的“英雄”。提倡高效率的工作方式。了解协同开发技术，比如 Woody Zuill 提出的 合作编程 Mob Programming 模式。遵从 4 个现代敏捷开发原则：用户至上、实践及快速学习、把安全放在首位、持续交付价值。每周为研发人员提供项目外的职业发展时间。把日工作记录作为一种驱动开发团队主动解决问题的方式。把同情心放在第一位。Corgibytes 公司让员工参加 Brene Brown 勇气工厂的培训是非常有用的。“如果公司高管和投资者不支持这种升级方式，你得从客户服务的角度去说服他们，”Goulet 说，“告诉他们通过这次调整后，最终产品将如何给公司的大多数客户提高更好的体验。这是你能做的一个很有力的论点。”寻找最具天才的代码重构者整个行业都认为顶尖的工程师不愿意干修复遗留代码的工作。他们只想着去开发新的东西。大家都说把他们留在维护部门真是太浪费人才了。其实这些都是误解。如果你知道去哪里和如何找工程师，并为他们提供一个愉快的工作环境，你就可以找到技术非常精湛的工程师，来帮你解决那些最棘手的技术债务问题。“每次在会议上，我们都会问现场的同事‘谁喜欢去在遗留代码上工作？’每次只有不到 10% 的与会者会举手。”Goulet 说。“但是我跟这些人交流后，我发现这些工程师恰好是喜欢最具挑战性工作的人才。”有一位客户来寻求她的帮助，他们使用国产的数据库，没有任何相关文档，也没有一种有效的方法来弄清楚他们公司的产品架构。她称修理这种情况的一类工程师为“修正者”。在 Corgibytes 公司，她有一支这样的修正者团队由她支配，热衷于通过研究二进制代码来解决技术问题。那么，如何才能找到这些技术人才呢？ Goulet 尝试过各种各样的方法，其中有一些方法还是富有成效的。她创办了一个社区网站 legacycode.rocks 并且在招聘启示上写道：“长期招聘那些喜欢重构遗留代码的另类开发人员...如果你以从事处理遗留代码的工作为自豪，欢迎加入！”“我开始收到很多人发来邮件说，‘噢，天呐，我也属于这样的开发人员！’”她说。“只需要发布这条信息，并且告诉他们这份工作是非常有意义的，就吸引了合适的人才。”在招聘的过程中，她也会使用持续性交付的经验来回答那些另类开发者想知道的信息：包括详细的工作内容以及明确的要求。“我这么做的原因是因为我讨厌重复性工作。如果我收到多封邮件来咨询同一个问题，我会把答案发布在网上，我感觉自己更像是在写说明文档一样。”但是随着时间的推移，她发现可以重新定义招聘流程来帮助她识别出更出色的候选人。比如说，她在应聘要求中写道，“公司 CEO 将会重新审查你的简历，因此请确保求职信中致意时不用写明性别。所有以‘尊敬的先生’或‘先生’开头的信件将会被当垃圾处理掉”。这些只是她的招聘初期策略。“我开始这么做是因为很多申请人把我当成男性，因为我是一家软件公司的男性 CEO，我必须是男性！？”Goulet 说。“所以，有一天我想我应该它当作应聘要求放到网上，看有多少人注意到这个问题。令我惊讶的是，这让我过滤掉一些不太严谨的申请人。还突显出了很多擅于从事遗留代码方面工作的人。”Goulet 想起一个应聘者发邮件给我说，“我查看了你们网站的代码（我喜欢这个网站，这也是我的工作）。你们的网站架构很奇特，好像是用 PHP 写的，但是你们却运行在用 Ruby 语言写的 Jekyll 下。我真的很好奇那是什么呢。”Goulet 从她的设计师那里得知，原来，在 HTML、CSS 和 JavaScript 文件中有一个未使用的 PHP 类名，她一直想解决这个问题，但是一直没机会。Goulet 的回复是：“你正在找工作吗？”另外一名候选人注意到她曾经在一篇说明文档中使用 CTO 这个词，但是她的团队里并没有这个头衔（她的合作伙伴是 Chief Code Whisperer）。这些注重细节、充满求知欲、积极主动的候选者更能引起她的注意。代码修正者不仅需要注重细节，而且这也是他们必备的品质。让人吃惊的是，Goulet 从来没有为招募最优秀的代码修正者而感到厌烦过。“大多数人都是通过我们的网站直接投递简历，但是当我们想扩大招聘范围的时候，我们会通过 PowerToFly 和 WeWorkRemotely 网站进行招聘。我现在确实不需要招募新人马了。他们需要经历一段很艰难的时期才能理解代码修正者的意义是什么。”如果他们通过首轮面试，Goulet 将会让候选者阅读一篇 Arlo Belshee 写的文章“ 命名是一个过程 Naming is a Process ”。它讲的是非常详细的处理遗留代码的的过程。她最经典的指导方法是：“阅读完这段代码并且告诉我，你是怎么理解的。”她将找出对问题的理解很深刻并且也愿意接受文章里提出的观点的候选者。这对于区分有深刻理解的候选者和仅仅想获得工作的候选者来说，是极其有用的办法。她强烈要求候选者找出一段与他操作相关的代码，来证明他是充满激情的、有主见的及善于分析问题的人。最后，她会让候选者跟公司里当前的团队成员一起使用 Exercism.io 工具进行编程。这是一个开源项目，它允许开发者学习如何在不同的编程语言环境下使用一系列的测试驱动开发的练习进行编程。结对编程课程的第一部分允许候选者选择其中一种语言来使用。下一个练习中，面试官可以选择一种语言进行编程。他们总能看到那些人处理异常的方法、随机应便的能力以及是否愿意承认某些自己不了解的技术。“当一个人真正的从执业者转变为大师的时候，他会毫不犹豫的承认自己不知道的东西，”Goulet说。让他们使用自己不熟悉的编程语言来写代码，也能衡量其坚韧不拔的毅力。“我们想听到某个人说，‘我会深入研究这个问题直到彻底解决它。’也许第二天他们仍然会跑过来跟我们说，‘我会一直留着这个问题直到我找到答案为止。’那是作为一个成功的修正者表现出来的一种气质。”产品开发人员在我们这个行业很受追捧，因此很多公司也想让他们来做维护工作。这是一个误解。最优秀的维护修正者并不是最好的产品开发工程师。如果一个有天赋的修正者在眼前，Goulet 懂得如何让他走向成功。下面是如何让这种类型的开发者感到幸福及高效工作的一些方式：给他们高度的自主权。把问题解释清楚，然后安排他们去完成，但是永不命令他们应该如何去解决问题。如果他们要求升级他们的电脑配置和相关工具，尽管去满足他们。他们明白什么样的需求才能最大限度地提高工作效率。帮助他们避免分心。他们喜欢全身心投入到某一个任务直至完成。总之，这些方法已经帮助 Corgibytes 公司培养出二十几位对遗留代码充满激情的专业开发者。稳定期没什么不好大多数创业公司都都不想跳过他们的成长期。一些公司甚至认为成长期应该是永无止境的。而且，他们觉得也没这个必要跳过成长期，即便他们已经进入到了下一个阶段：稳定期。完全进入到稳定期意味着你拥有人力资源及管理方法来创造技术财富，同时根据优先权适当支出。“在成长期和稳定期之间有个转折点，就是维护人员必须要足够壮大，并且相对于专注新功能的产品开发人员，你开始更公平的对待维护人员，”Goulet 说。“你们公司的产品开发完成了。现在你得让他们更加稳定地运行。”这就意味着要把公司更多的预算分配到产品维护及现代化方面。“你不应该把产品维护当作是一个不值得关注的项目，”她说。“这必须成为你们公司固有的一种企业文化 —— 这将帮助你们公司将来取得更大的成功。“最终，你通过这些努力创建的技术财富，将会为你的团队带来一大批全新的开发者：他们就像侦查兵一样，有充足的时间和资源去探索新的领域，挖掘新客户资源并且给公司创造更多的机遇。当你们在新的市场领域做得更广泛并且不断取得进展 —— 那么你们公司已经真正地进入到繁荣发展的状态了。via: http://firstround.com/review/forget-technical-debt-heres-how-to-build-technical-wealth/作者：http://firstround.com/ 译者：rusking 校对：jasminepeng本文由 LCTT 原创编译，Linux中国 荣誉推出
本教程的第 2 部分将介绍如何使用 Dovecot 将邮件从 Postfix 服务器移动到用户的收件箱。在第一部分中，我们安装并测试了 Postfix SMTP 服务器。Postfix 或任何 SMTP 服务器都不是一个完整的邮件服务器，因为它所做的只是在 SMTP 服务器之间移动邮件。我们需要 Dovecot 将邮件从 Postfix 服务器移动到用户的收件箱中。Dovecot 支持两种标准邮件协议：IMAP（Internet 邮件访问协议）和 POP3（邮局协议）。 IMAP 服务器会在服务器上保留所有邮件。您的用户可以选择将邮件下载到计算机或仅在服务器上访问它们。 IMAP 对于有多台机器的用户是方便的。但对你而言需要更多的工作，因为你必须确保你的服务器始终可用，而且 IMAP 服务器需要大量的存储和内存。POP3 是较旧的协议。POP3 服务器可以比 IMAP 服务器服务更多的用户，因为邮件会下载到用户的计算机。大多数邮件客户端可以选择在服务器上保留一定天数的邮件，因此 POP3 的行为有点像 IMAP。但它又不是 IMAP，当你像 IMAP 那样（在多台计算机上使用它时）那么常常会下载多次或意外删除。安装 Dovecot启动你的 Ubuntu 系统并安装 Dovecot：$ sudo apt-get install dovecot-imapd dovecot-pop3d 它会安装可用的配置，并在完成后自动启动，你可以用 ps ax | grep dovecot 确认：$ ps ax | grep dovecot 15988 ? Ss 0:00 /usr/sbin/dovecot 15990 ? S 0:00 dovecot/anvil 15991 ? S 0:00 dovecot/log 打开你的 Postfix 配置文件 /etc/postfix/main.cf，确保配置了maildir 而不是 mbox 的邮件存储方式，mbox 是给每个用户一个单一大文件，而 maildir 是每条消息都存储为一个文件。大量的小文件比一个庞大的文件更稳定且易于管理。添加如下两行，第二行告诉 Postfix 你需要 maildir 格式，并且在每个用户的家目录下创建一个 .Mail 目录。你可以取任何名字，不一定要是 .Mail：mail_spool_directory = /var/mail home_mailbox = .Mail/ 现在调整你的 Dovecot 配置。首先把原始的 dovecot.conf 文件重命名放到一边，因为它会调用存放在 conf.d 中的文件，在你刚刚开始学习时把配置放一起更简单些：$ sudo mv /etc/dovecot/dovecot.conf /etc/dovecot/dovecot-oldconf 现在创建一个新的 /etc/dovecot/dovecot.conf：disable_plaintext_auth = no mail_location = maildir:~/.Mail namespace inbox { inbox = yes mailbox Drafts { special_use = \Drafts } mailbox Sent { special_use = \Sent } mailbox Trash { special_use = \Trash } } passdb { driver = pam } protocols = " imap pop3" ssl = no userdb { driver = passwd } 注意 mail_location = maildir 必须和 main.cf 中的 home_mailbox 参数匹配。保存你的更改并重新加载 Postfix 和 Dovecot 配置：$ sudo postfix reload $ sudo dovecot reload 快速导出配置使用下面的命令来快速查看你的 Postfix 和 Dovecot 配置：$ postconf -n $ doveconf -n 测试 Dovecot现在再次启动 telnet，并且给自己发送一条测试消息。粗体显示的是你输入的命令。studio 是我服务器的主机名，因此你必须用自己的：$ telnet studio 25 Trying 127.0.1.1... Connected to studio. Escape character is '^]'. 220 studio.router ESMTP Postfix (Ubuntu) EHLO studio 250-studio.router 250-PIPELINING 250-SIZE 10240000 250-VRFY 250-ETRN 250-STARTTLS 250-ENHANCEDSTATUSCODES 250-8BITMIME 250-DSN 250 SMTPUTF8 mail from: tester@test.net 250 2.1.0 Ok rcpt to: carla@studio 250 2.1.5 Ok data 354 End data with .Date: November 25, 2016 From: tester Message-ID: first-test Subject: mail server test Hi carla, Are you reading this? Let me know if you didn't get this. . 250 2.0.0 Ok: queued as 0C261A1F0F quit 221 2.0.0 Bye Connection closed by foreign host. 现在请求 Dovecot 来取回你的新消息，使用你的 Linux 用户名和密码登录：$ telnet studio 110 Trying 127.0.0.1... Connected to studio. Escape character is '^]'. +OK Dovecot ready. user carla +OK pass password +OK Logged in. stat +OK 2 809 list +OK 2 messages: 1 383 2 426 . retr 2 +OK 426 octets Return-Path: <tester@test.net> X-Original-To: carla@studio Delivered-To: carla@studio Received: from studio (localhost [127.0.0.1]) by studio.router (Postfix) with ESMTP id 0C261A1F0F for <carla@studio>; Wed, 30 Nov 2016 17:18:57 -0800 (PST) Date: November 25, 2016 From: tester@studio.router Message-ID: first-test Subject: mail server test Hi carla, Are you reading this? Let me know if you didn't get this. . quit +OK Logging out. Connection closed by foreign host. 花一点时间比较第一个例子中输入的消息和第二个例子中接收的消息。 返回地址和日期是很容易伪造的，但 Postfix 不会被愚弄。大多数邮件客户端默认显示一个最小的标头集，但是你需要读取完整的标头才能查看真实的回溯。你也可以在你的 ~/Mail/cur 目录中查看你的邮件，它们是普通文本，我已经有两封测试邮件：$ ls .Mail/cur/ 1480540325.V806I28e0229M351743.studio:2,S 1480555224.V806I28e000eM41463.studio:2,S 测试 IMAP我们 Dovecot 同时启用了 POP3 和 IMAP 服务，因此让我们使用 telnet 测试 IMAP。$ telnet studio imap2 Trying 127.0.1.1... Connected to studio. Escape character is '^]'. * OK [CAPABILITY IMAP4rev1 LITERAL+ SASL-IR LOGIN-REFERRALS ID ENABLE IDLE AUTH=PLAIN] Dovecot ready. A1 LOGIN carla password A1 OK [CAPABILITY IMAP4rev1 LITERAL+ SASL-IR LOGIN-REFERRALS ID ENABLE IDLE SORT SORT=DISPLAY THREAD=REFERENCES THREAD=REFS THREAD=ORDEREDSUBJECT MULTIAPPEND URL-PARTIAL CATENATE UNSELECT CHILDREN NAMESPACE UIDPLUS LIST-EXTENDED I18NLEVEL=1 CONDSTORE QRESYNC ESEARCH ESORT SEARCHRES WITHIN CONTEXT=SEARCH LIST-STATUS BINARY MOVE SPECIAL-USE] Logged in A2 LIST "" "*" * LIST (\HasNoChildren) "." INBOX A2 OK List completed (0.000 + 0.000 secs). A3 EXAMINE INBOX * FLAGS (\Answered \Flagged \Deleted \Seen \Draft) * OK [PERMANENTFLAGS ()] Read-only mailbox. * 2 EXISTS * 0 RECENT * OK [UIDVALIDITY 1480539462] UIDs valid * OK [UIDNEXT 3] Predicted next UID * OK [HIGHESTMODSEQ 1] Highest A3 OK [READ-ONLY] Examine completed (0.000 + 0.000 secs). A4 logout * BYE Logging out A4 OK Logout completed. Connection closed by foreign host Thunderbird 邮件客户端图 1 中的屏幕截图显示了我局域网上另一台主机上的图形邮件客户端中的邮件。图 1： Thunderbird mail此时，你已有一个可以工作的 IMAP 和 POP3 邮件服务器，并且你也知道该如何测试你的服务器。你的用户可以在他们设置邮件客户端时选择要使用的协议。如果您只想支持一个邮件协议，那么只需要在您的 Dovecot 配置中留下你要的协议名字。然而，这还远远没有完成。这是一个非常简单、没有加密的、大门敞开的安装。它也只适用于与邮件服务器在同一系统上的用户。这是不可扩展的，并具有一些安全风险，例如没有密码保护。 我们会在下篇了解如何创建与系统用户分开的邮件用户，以及如何添加加密。via: https://www.linux.com/learn/sysadmin/building-email-server-ubuntu-linux-part-2作者：CARLA SCHRODER 译者：geekpi 校对：wxy本文由 LCTT 原创编译，Linux中国 荣誉推出
现在让我们强化你的服务器以防止未授权访问。经常升级系统保持最新的软件是你可以在任何操作系统上采取的最大的安全预防措施。软件更新的范围从关键漏洞补丁到小 bug 的修复，许多软件漏洞实际上是在它们被公开的时候得到修补的。自动安全更新有一些用于服务器上自动更新的参数。Fedora 的 Wiki 上有一篇很棒的剖析自动更新的利弊的文章，但是如果你把它限制到安全更新上，自动更新的风险将是最小的。自动更新的可行性必须你自己判断，因为它归结为你在你的服务器上做什么。请记住，自动更新仅适用于来自仓库的包，而不是自行编译的程序。你可能会发现一个复制了生产服务器的测试环境是很有必要的。可以在部署到生产环境之前，在测试环境里面更新来检查问题。CentOS 使用 yum-cron 进行自动更新。Debian 和 Ubuntu 使用 无人值守升级。Fedora 使用 dnf-automatic。添加一个受限用户账户到目前为止，你已经作为 root 用户访问了你的服务器，它有无限制的权限，可以执行任何命令 - 甚至可能意外中断你的服务器。 我们建议创建一个受限用户帐户，并始终使用它。 管理任务应该使用 sudo 来完成，它可以临时提升受限用户的权限，以便管理你的服务器。不是所有的 Linux 发行版都在系统上默认包含 sudo，但大多数都在其软件包仓库中有 sudo。 如果得到这样的输出 sudo：command not found，请在继续之前安装 sudo。要添加新用户，首先通过 SSH 登录到你的服务器。CentOS / Fedora1、 创建用户，用你想要的名字替换 example_user，并分配一个密码：useradd example_user && passwd example_user 2、 将用户添加到具有 sudo 权限的 wheel 组：usermod -aG wheel example_user Ubuntu1、 创建用户，用你想要的名字替换 example_user。你将被要求输入用户密码：adduser example_user 2、 添加用户到 sudo 组，这样你就有管理员权限了：adduser example_user sudo Debian1、 Debian 默认的包中没有 sudo， 使用 apt-get 来安装：apt-get install sudo 2、 创建用户，用你想要的名字替换 example_user。你将被要求输入用户密码：adduser example_user 3、 添加用户到 sudo 组，这样你就有管理员权限了：adduser example_user sudo 创建完有限权限的用户后，断开你的服务器连接：exit 重新用你的新用户登录。用你的用户名代替 example_user，用你的服务器 IP 地址代替例子中的 IP 地址：ssh example_user@203.0.113.10 现在你可以用你的新用户帐户管理你的服务器，而不是 root。 几乎所有超级用户命令都可以用 sudo（例如：sudo iptables -L -nv）来执行，这些命令将被记录到 /var/log/auth.log 中。加固 SSH 访问默认情况下，密码认证用于通过 SSH 连接到您的服务器。加密密钥对更加安全，因为它用私钥代替了密码，这通常更难以暴力破解。在本节中，我们将创建一个密钥对，并将服务器配置为不接受 SSH 密码登录。创建验证密钥对1、这是在你本机上完成的，不是在你的服务器上，这里将创建一个 4096 位的 RSA 密钥对。在创建过程中，您可以选择使用密码加密私钥。这意味着它不能在没有输入密码的情况下使用，除非将密码保存到本机桌面的密钥管理器中。我们建议您使用带有密码的密钥对，但如果你不想使用密码，则可以将此字段留空。Linux / OS X如果你已经创建了 RSA 密钥对，则这个命令将会覆盖它，这可能会导致你不能访问其它的操作系统。如果你已创建过密钥对，请跳过此步骤。要检查现有的密钥，请运行 ls〜/ .ssh / id_rsa *。ssh-keygen -b 4096 在输入密码之前，按下 回车使用 /home/your_username/.ssh 中的默认名称 id_rsa 和 id_rsa.pub。Windows这可以使用 PuTTY 完成，在我们指南中已有描述：使用 SSH 公钥验证。2、将公钥上传到您的服务器上。 将 example_user 替换为你用来管理服务器的用户名称，将 203.0.113.10 替换为你的服务器的 IP 地址。Linux在本机上：ssh-copy-id example_user@203.0.113.10 OS X在你的服务器上（用你的权限受限用户登录）：mkdir -p ~/.ssh && sudo chmod -R 700 ~/.ssh/ 在本机上：scp ~/.ssh/id_rsa.pub example_user@203.0.113.10:~/.ssh/authorized_keys 如果相对于 scp 你更喜欢 ssh-copy-id 的话，那么它也可以在 Homebrew 中找到。使用 brew install ssh-copy-id 安装。Windows选择 1：使用 WinSCP 来完成。 在登录窗口中，输入你的服务器的 IP 地址作为主机名，以及非 root 的用户名和密码。单击“登录”连接。一旦 WinSCP 连接后，你会看到两个主要部分。 左边显示本机上的文件，右边显示服务区上的文件。 使用左侧的文件浏览器，导航到你已保存公钥的文件，选择公钥文件，然后点击上面工具栏中的“上传”。系统会提示你输入要将文件放在服务器上的路径。 将文件上传到 /home/example_user/.ssh /authorized_keys，用你的用户名替换 example_user。选择 2：将公钥直接从 PuTTY 键生成器复制到连接到你的服务器中（作为非 root 用户）：mkdir ~/.ssh; nano ~/.ssh/authorized_keys 上面命令将在文本编辑器中打开一个名为 authorized_keys 的空文件。 将公钥复制到文本文件中，确保复制为一行，与 PuTTY 所生成的完全一样。 按下 CTRL + X，然后按下 Y，然后回车保存文件。最后，你需要为公钥目录和密钥文件本身设置权限：sudo chmod 700 -R ~/.ssh && chmod 600 ~/.ssh/authorized_keys 这些命令通过阻止其他用户访问公钥目录以及文件本身来提供额外的安全性。有关它如何工作的更多信息，请参阅我们的指南如何修改文件权限。3、 现在退出并重新登录你的服务器。如果你为私钥指定了密码，则需要输入密码。SSH 守护进程选项1、 不允许 root 用户通过 SSH 登录。 这要求所有的 SSH 连接都是通过非 root 用户进行。当以受限用户帐户连接后，可以通过使用 sudo 或使用 su - 切换为 root shell 来使用管理员权限。# Authentication: ... PermitRootLogin no 2、 禁用 SSH 密码认证。 这要求所有通过 SSH 连接的用户使用密钥认证。根据 Linux 发行版的不同，它可能需要添加 PasswordAuthentication 这行，或者删除前面的 # 来取消注释。# Change to no to disable tunnelled clear text passwords PasswordAuthentication no 如果你从许多不同的计算机连接到服务器，你可能想要继续启用密码验证。这将允许你使用密码进行身份验证，而不是为每个设备生成和上传密钥对。3、 只监听一个互联网协议。 在默认情况下，SSH 守护进程同时监听 IPv4 和 IPv6 上的传入连接。除非你需要使用这两种协议进入你的服务器，否则就禁用你不需要的。 这不会禁用系统范围的协议，它只用于 SSH 守护进程。使用选项：AddressFamily inet 只监听 IPv4。AddressFamily inet6 只监听 IPv6。默认情况下，AddressFamily 选项通常不在 sshd_config 文件中。将它添加到文件的末尾：echo 'AddressFamily inet' | sudo tee -a /etc/ssh/sshd_config 4、 重新启动 SSH 服务以加载新配置。如果你使用的 Linux 发行版使用 systemd（CentOS 7、Debian 8、Fedora、Ubuntu 15.10+）sudo systemctl restart sshd 如果您的 init 系统是 SystemV 或 Upstart（CentOS 6、Debian 7、Ubuntu 14.04）：sudo service ssh restart 使用 Fail2Ban 保护 SSH 登录Fail2Ban 是一个应用程序，它会在太多的失败登录尝试后禁止 IP 地址登录到你的服务器。由于合法登录通常不会超过三次尝试（如果使用 SSH 密钥，那不会超过一个），因此如果服务器充满了登录失败的请求那就表示有恶意访问。Fail2Ban 可以监视各种协议，包括 SSH、HTTP 和 SMTP。默认情况下，Fail2Ban 仅监视 SSH，并且因为 SSH 守护程序通常配置为持续运行并监听来自任何远程 IP 地址的连接，所以对于任何服务器都是一种安全威慑。有关安装和配置 Fail2Ban 的完整说明，请参阅我们的指南：使用 Fail2ban 保护服务器。删除未使用的面向网络的服务大多数 Linux 发行版都安装并运行了网络服务，监听来自互联网、回环接口或两者兼有的传入连接。 将不需要的面向网络的服务从系统中删除，以减少对运行进程和对已安装软件包攻击的概率。查明运行的服务要查看服务器中运行的服务：sudo netstat -tulpn 如果默认情况下 netstat 没有包含在你的 Linux 发行版中，请安装软件包 net-tools 或使用 ss -tulpn 命令。以下是 netstat 的输出示例。 请注意，因为默认情况下不同发行版会运行不同的服务，你的输出将有所不同：Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name tcp 0 0 0.0.0.0:111 0.0.0.0:* LISTEN 7315/rpcbind tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN 3277/sshd tcp 0 0 127.0.0.1:25 0.0.0.0:* LISTEN 3179/exim4 tcp 0 0 0.0.0.0:42526 0.0.0.0:* LISTEN 2845/rpc.statd tcp6 0 0 :::48745 :::* LISTEN 2845/rpc.statd tcp6 0 0 :::111 :::* LISTEN 7315/rpcbind tcp6 0 0 :::22 :::* LISTEN 3277/sshd tcp6 0 0 ::1:25 :::* LISTEN 3179/exim4 udp 0 0 127.0.0.1:901 0.0.0.0:* 2845/rpc.statd udp 0 0 0.0.0.0:47663 0.0.0.0:* 2845/rpc.statd udp 0 0 0.0.0.0:111 0.0.0.0:* 7315/rpcbind udp 0 0 192.0.2.1:123 0.0.0.0:* 3327/ntpd udp 0 0 127.0.0.1:123 0.0.0.0:* 3327/ntpd udp 0 0 0.0.0.0:123 0.0.0.0:* 3327/ntpd udp 0 0 0.0.0.0:705 0.0.0.0:* 7315/rpcbind udp6 0 0 :::111 :::* 7315/rpcbind udp6 0 0 fe80::f03c:91ff:fec:123 :::* 3327/ntpd udp6 0 0 2001:DB8::123 :::* 3327/ntpd udp6 0 0 ::1:123 :::* 3327/ntpd udp6 0 0 :::123 :::* 3327/ntpd udp6 0 0 :::705 :::* 7315/rpcbind udp6 0 0 :::60671 :::* 2845/rpc.statd netstat 告诉我们服务正在运行 RPC（rpc.statd 和 rpcbind）、SSH（sshd）、NTPdate（ntpd）和Exim（exim4）。TCP请参阅 netstat 输出的 Local Address 那一列。进程 rpcbind 正在侦听 0.0.0.0:111 和 :::111，外部地址是 0.0.0.0:* 或者 :::* 。这意味着它从任何端口和任何网络接口接受来自任何外部地址（IPv4 和 IPv6）上的其它 RPC 客户端的传入 TCP 连接。 我们看到类似的 SSH，Exim 正在侦听来自回环接口的流量，如所示的 127.0.0.1 地址。UDPUDP 套接字是无状态的，这意味着它们只有打开或关闭，并且每个进程的连接是独立于前后发生的连接。这与 TCP 的连接状态（例如 LISTEN、ESTABLISHED和 CLOSE_WAIT）形成对比。我们的 netstat输出说明 NTPdate ：1）接受服务器的公网 IP 地址的传入连接；2）通过本地主机进行通信；3）接受来自外部的连接。这些连接是通过端口 123 进行的，同时支持 IPv4 和 IPv6。我们还看到了 RPC 打开的更多的套接字。查明该移除哪个服务如果你在没有启用防火墙的情况下对服务器进行基本的 TCP 和 UDP 的 nmap 扫描，那么在打开端口的结果中将出现 SSH、RPC 和 NTPdate 。通过配置防火墙，你可以过滤掉这些端口，但 SSH 除外，因为它必须允许你的传入连接。但是，理想情况下，应该禁用未使用的服务。你可能主要通过 SSH 连接管理你的服务器，所以让这个服务需要保留。如上所述，RSA 密钥和 Fail2Ban 可以帮助你保护 SSH。NTP 是服务器计时所必需的，但有个替代 NTPdate 的方法。如果你喜欢不开放网络端口的时间同步方法，并且你不需要纳秒精度，那么你可能有兴趣用 OpenNTPD 来代替 NTPdate。然而，Exim 和 RPC 是不必要的，除非你有特定的用途，否则应该删除它们。本节针对 Debian 8。默认情况下，不同的 Linux 发行版具有不同的服务。如果你不确定某项服务的功能，请尝试搜索互联网以了解该功能是什么，然后再尝试删除或禁用它。卸载监听的服务如何移除包取决于发行版的包管理器：Archsudo pacman -Rs package_name CentOSsudo yum remove package_name Debian / Ubuntusudo apt-get purge package_name Fedorasudo dnf remove package_name 再次运行 sudo netstat -tulpn，你看到监听的服务就只会有 SSH（sshd）和 NTP（ntpdate，网络时间协议）。配置防火墙使用防火墙阻止不需要的入站流量能为你的服务器提供一个高效的安全层。 通过指定入站流量，你可以阻止入侵和网络测绘。 最佳做法是只允许你需要的流量，并拒绝一切其他流量。请参阅我们的一些关于最常见的防火墙程序的文档：iptables 是 netfilter 的控制器，它是 Linux 内核的包过滤框架。 默认情况下，iptables 包含在大多数 Linux 发行版中。firewallD 是可用于 CentOS/Fedora 系列发行版的 iptables 控制器。UFW 为 Debian 和 Ubuntu 提供了一个 iptables 前端。接下来这些是加固 Linux 服务器的最基本步骤，但是进一步的安全层将取决于其预期用途。 其他技术可以包括应用程序配置，使用入侵检测或者安装某个形式的访问控制。现在你可以按你的需求开始设置你的服务器了。via: https://www.linode.com/docs/security/securing-your-server/作者：Phil Zona 译者：geekpi 校对：wxy本文由 LCTT 原创编译，Linux中国 荣誉推出
介绍在这篇指南中，我将向你介绍一个集成开发环境 - PyCharm， 你可以在它上面使用 Python 编程语言开发专业应用。Python 是一门优秀的编程语言，因为它真正实现了跨平台，用它开发的应用程序在 Windows、Linux 以及 Mac 系统上均可运行，无需重新编译任何代码。PyCharm 是由 Jetbrains 开发的一个编辑器和调试器，Jetbrains 就是那个开发了 Resharper 的公司。不得不说，Resharper 是一个很优秀的工具，它被 Windows 开发者们用来重构代码，同时，它也使得 Windows 开发者们写 .NET 代码更加轻松。Resharper 的许多原则也被加入到了 PyCharm 专业版中。如何安装 PyCharm我已经写了一篇关于如何获取 PyCharm 的指南，下载、解压文件，然后运行。欢迎界面当你第一次运行 PyCharm 或者关闭一个项目的时候，会出现一个屏幕，上面显示一系列近期项目。你也会看到下面这些菜单选项：创建新项目打开项目从版本控制仓库检出还有一个配置设置选项，你可以通过它设置默认 Python 版本或者一些其他设置。创建一个新项目当你选择‘创建一个新项目’以后，它会提供下面这一系列可能的项目类型供你选择：Pure PythonDjangoFlaskGoogle App EnginePyramidWeb2PyAngular CLIAngularJSFoundationHTML5 BolierplateReact Starter KitTwitter BootstrapWeb Starter Kit这不是一个编程教程，所以我没必要说明这些项目类型是什么。如果你想创建一个可以运行在 Windows、Linux 和 Mac 上的简单桌面运行程序，那么你可以选择 Pure Python 项目，然后使用 Qt 库来开发图形应用程序，这样的图形应用程序无论在何种操作系统上运行，看起来都像是原生的，就像是在该系统上开发的一样。选择了项目类型以后，你需要输入一个项目名字并且选择一个 Python 版本来进行开发。打开一个项目你可以通过单击‘最近打开的项目’列表中的项目名称来打开一个项目，或者，你也可以单击‘打开’，然后浏览到你想打开的项目所在的文件夹，找到该项目，然后选择‘确定’。从源码控制进行查看PyCharm 提供了从各种在线资源查看项目源码的选项，在线资源包括 GitHub、CVS、Git、Mercurial 以及 Subversion。PyCharm IDE（集成开发环境）PyCharm IDE 中可以打开顶部的菜单，在这个菜单下方你可以看到每个打开的项目的标签。屏幕右方是调试选项区，可以单步运行代码。左侧面板有项目文件和外部库的列表。如果想在项目中新建一个文件，你可以鼠标右击项目的名字，然后选择‘新建’。然后你可以在下面这些文件类型中选择一种添加到项目中：文件目录Python 包Python 包Jupyter 笔记HTML 文件StylesheetJavaScriptTypeScriptCoffeeScriptGherkin数据源当添加了一个文件，比如 Python 文件以后，你可以在右边面板的编辑器中进行编辑。文本是全彩色编码的，并且有黑体文本。垂直线显示缩进，从而能够确保缩进正确。编辑器具有智能补全功能，这意味着当你输入库名字或可识别命令的时候，你可以按 'Tab' 键补全命令。调试程序你可以利用屏幕右上角的’调试选项’调试程序的任何一个地方。如果你是在开发一个图形应用程序，你可以点击‘绿色按钮’来运行程序，你也可以通过 'shift+F10' 快捷键来运行程序。为了调试应用程序，你可以点击紧挨着‘绿色按钮’的‘绿色箭头’或者按 ‘shift+F9’ 快捷键。你可以点击一行代码的灰色边缘，从而设置断点，这样当程序运行到这行代码的时候就会停下来。你可以按 'F8' 单步向前运行代码，这意味着你只是运行代码但无法进入函数内部，如果要进入函数内部，你可以按 'F7'。如果你想从一个函数中返回到调用函数，你可以按 'shift+F8'。调试过程中，你会在屏幕底部看到许多窗口，比如进程和线程列表，以及你正在监视的变量。当你运行到一行代码的时候，你可以对这行代码中出现的变量进行监视，这样当变量值改变的时候你能够看到。另一个不错的选择是使用覆盖检查器运行代码。在过去这些年里，编程界发生了很大的变化，现在，对于开发人员来说，进行测试驱动开发是很常见的，这样他们可以检查对程序所做的每一个改变，确保不会破坏系统的另一部分。覆盖检查器能够很好的帮助你运行程序，执行一些测试，运行结束以后，它会以百分比的形式告诉你测试运行所覆盖的代码有多少。还有一个工具可以显示‘类函数’或‘类’的名字，以及一个项目被调用的次数和在一个特定代码片段运行所花费的时间。代码重构PyCharm 一个很强大的特性是代码重构选项。当你开始写代码的时候，会在右边缘出现一个小标记。如果你写的代码可能出错或者写的不太好， PyCharm 会标记上一个彩色标记。点击彩色标记将会告诉你出现的问题并提供一个解决方法。比如，你通过一个导入语句导入了一个库，但没有使用该库中的任何东西，那么不仅这行代码会变成灰色，彩色标记还会告诉你‘该库未使用’。对于正确的代码，也可能会出现错误提示，比如在导入语句和函数起始之间只有一个空行。当你创建了一个名称非小写的函数时它也会提示你。你不必遵循 PyCharm 的所有规则。这些规则大部分只是好的编码准则，与你的代码是否能够正确运行无关。代码菜单还有其它的重构选项。比如，你可以进行代码清理以及检查文件或项目问题。总结PyCharm 是 Linux 系统上开发 Python 代码的一个优秀编辑器，并且有两个可用版本。社区版可供临时开发者使用，专业版则提供了开发者开发专业软件可能需要的所有工具。via: https://www.lifewire.com/pycharm-the-best-linux-python-ide-4091045作者：Gary Newell 译者：ucasFL 校对：wxy本文由 LCTT 组织编译，Linux中国 荣誉推出
最近几年，数量庞大的个人和组织放弃 Windows 平台选择 Linux 平台，而且随着人们体验到更多 Linux 的发展，这个数字将会继续增长。在很长的一段时间内， Linux 是网络服务器的领导者，因为大部分的网络服务器都运行在 Linux 之上，这或许是为什么那么多的个人和组织选择迁移的一个原因。迁移的原因有很多，更强的平台稳定性、可靠性、成本、所有权和安全性等等。随着更多的个人和组织迁移到 Linux 平台，MS SQL 服务器数据库管理系统的迁移也有着同样的趋势，首选的是 MySQL ，这是因为 MySQL 的互用性、平台无关性和购置成本低。有如此多的个人和组织完成了迁移，这是应业务需求而产生的迁移，而不是为了迁移的乐趣。因此，有必要做一个综合可行性和成本效益分析，以了解迁移对于你的业务上的正面和负面影响。迁移需要基于以下重要因素：对平台的掌控不像 Windows 那样，你不能完全控制版本发布和修复，而 Linux 可以让你需要需要修复的时候真正给了你获取修复的灵活性。这一点受到了开发者和安全人员的喜爱，因为他们能在一个安全威胁被确定时立即自行打补丁，不像 Windows ，你只能期望官方尽快发布补丁。跟随大众目前， 运行在 Linux 平台上的服务器在数量上远超 Windows，几乎是全世界服务器数量的四分之三，而且这种趋势在最近一段时间内不会改变。因此，许多组织正在将他们的服务完全迁移到 Linux 上，而不是同时使用两种平台，同时使用将会增加他们的运营成本。微软没有开放 SQL Server 的源代码微软宣称他们下一个名为 Denali 的新版 MS SQL Server 将会是一个 Linux 版本，并且不会开放其源代码，这意味着他们仍然使用的是软件授权模式，只是新版本将能在 Linux 上运行而已。这一点将许多乐于接受开源新版本的人拒之门外。这也没有给那些使用闭源的 Oracle 用户另一个选择，对于使用完全开源的 MySQL 用户也是如此。节约授权许可证的花费授权许可证的潜在成本让许多用户很失望。在 Windows 平台上运行 MS SQL 服务器有太多的授权许可证牵涉其中。你需要这些授权许可证：Windows 操作系统MS SQL 服务器特定的数据库工具，例如 SQL 分析工具等不像 Windows 平台，Linux 完全没有高昂的授权花费，因此更能吸引用户。 MySQL 数据库也能免费获取，甚而它提供了像 MS SQL 服务器一样的灵活性，那就更值得选择了。不像那些给 MS SQL 设计的收费工具，大部分的 MySQL 数据库实用程序是免费的。有时候用的是特殊的硬件因为 Linux 是不同的开发者所开发，并在不断改进中，所以它独立于所运行的硬件之上，并能被广泛使用在不同的硬件平台。然而尽管微软正在努力让 Windows 和 MSSQL 服务器做到硬件无关，但在平台无关上依旧有些限制。支持有了 Linux、MySQL 和其它的开源软件，获取满足自己特定需求的帮助变得更加简单，因为有不同开发者参与到这些软件的开发过程中。这些开发者或许就在你附近，这样更容易获取帮助。在线论坛也能帮上不少，你能发帖并讨论你所面对的问题。至于那些商业软件，你只能根据他们的软件协议和时间来获得帮助，有时候他们不能在你的时间范围内给出一个解决方案。在不同的情况中，迁移到 Linux 都是你最好的选择，加入一个彻底的、稳定可靠的平台来获取优异表现，众所周知，它比 Windows 更健壮。这值得一试。via: https://www.howtoforge.com/tutorial/moving-with-sql-server-to-linux-move-from-sql-server-to-mysql-as-well/作者：Tony Branson 译者：ypingcn 校对：wxy本文由 LCTT 组织编译，Linux中国 荣誉推出
这是 LXD 2.0 系列介绍文章的第四篇。LXD 入门安装与配置你的第一个 LXD 容器资源控制镜像管理远程主机及容器迁移LXD 中的 DockerLXD 中的 LXD实时迁移LXD 和 JujuLXD 和 OpenStack调试，及给 LXD 做贡献因为 LXD 容器管理有很多命令，因此这篇文章会很长。 如果你想要快速地浏览这些相同的命令，你可以尝试下我们的在线演示！可用资源限制LXD 提供了各种资源限制。其中一些与容器本身相关，如内存配额、CPU 限制和 I/O 优先级。而另外一些则与特定设备相关，如 I/O 带宽或磁盘用量限制。与所有 LXD 配置一样，资源限制可以在容器运行时动态更改。某些可能无法启用，例如，如果设置的内存值小于当前内存用量，但 LXD 将会试着设置并且报告失败。所有的限制也可以通过配置文件继承，在这种情况下每个受影响的容器将受到该限制的约束。也就是说，如果在默认配置文件中设置 limits.memory=256MB，则使用默认配置文件（通常是全都使用）的每个容器的内存限制为 256MB。我们不支持资源限制池，将其中的限制由一组容器共享，因为我们没有什么好的方法通过现有的内核 API 实现这些功能。磁盘这或许是最需要和最明显的需求。只需设置容器文件系统的大小限制，并对容器强制执行。LXD 确实可以让你这样做！不幸的是，这比它听起来复杂得多。 Linux 没有基于路径的配额，而大多数文件系统只有基于用户和组的配额，这对容器没有什么用处。如果你正在使用 ZFS 或 btrfs 存储后端，这意味着现在 LXD 只能支持磁盘限制。也有可能为 LVM 实现此功能，但这取决于与它一起使用的文件系统，并且如果结合实时更新那会变得棘手起来，因为并不是所有的文件系统都允许在线增长，而几乎没有一个允许在线收缩。CPU当涉及到 CPU 的限制，我们支持 4 种不同的东西：只给我 X 个 CPU 核心在这种模式下，你让 LXD 为你选择一组核心，然后为更多的容器和 CPU 的上线/下线提供负载均衡。容器只看到这个数量的 CPU 核心。给我一组特定的 CPU 核心（例如，核心1、3 和 5）类似于第一种模式，但是不会做负载均衡，你会被限制在那些核心上，无论它们有多忙。给我你拥有的 20％ 处理能力在这种模式下，你可以看到所有的 CPU，但调度程序将限制你使用 20％ 的 CPU 时间，但这只有在负载状态才会这样！所以如果系统不忙，你的容器可以跑得很欢。而当其他的容器也开始使用 CPU 时，它会被限制用量。每测量 200ms，给我 50ms（并且不超过）此模式与上一个模式类似，你可以看到所有的 CPU，但这一次，无论系统可能是多么空闲，你只能使用你设置的极限时间下的尽可能多的 CPU 时间。在没有过量使用的系统上，这可使你可以非常整齐地分割 CPU，并确保这些容器的持续性能。另外还可以将前两个中的一个与最后两个之一相结合，即请求一组 CPU，然后进一步限制这些 CPU 的 CPU 时间。除此之外，我们还有一个通用的优先级调节方式，可以告诉调度器当你处于负载状态时，两个争夺资源的容器谁会取得胜利。内存内存听起来很简单，就是给我多少 MB 的内存！它绝对可以那么简单。 我们支持这种限制以及基于百分比的请求，比如给我 10％ 的主机内存！另外我们在上层支持一些额外的东西。 例如，你可以选择在每个容器上打开或者关闭 swap，如果打开，还可以设置优先级，以便你可以选择哪些容器先将内存交换到磁盘！内存限制默认是“hard”。 也就是说，当内存耗尽时，内核将会开始杀掉你的那些进程。或者，你可以将强制策略设置为“soft”，在这种情况下，只要没有别的进程的情况下，你将被允许使用尽可能多的内存。一旦别的进程想要这块内存，你将无法分配任何内存，直到你低于你的限制或者主机内存再次有空余。网络 I/O网络 I/O 可能是我们看起来最简单的限制，但是相信我，实现真的不简单！我们支持两种限制。 第一个是对网络接口的速率限制。你可以设置入口和出口的限制，或者只是设置“最大”限制然后应用到出口和入口。这个只支持“桥接”和“p2p”类型接口。第二种是全局网络 I/O 优先级，仅当你的网络接口趋于饱和的时候再使用。块 I/O我把最古怪的放在最后。对于用户看起来它可能简单，但有一些情况下，它的结果并不会和你的预期一样。我们在这里支持的基本上与我在网络 I/O 中描述的相同。你可以直接设置磁盘的读写 IO 的频率和速率，并且有一个全局的块 I/O 优先级，它会通知 I/O 调度程序更倾向哪个。古怪的是如何设置以及在哪里应用这些限制。不幸的是，我们用于实现这些功能的底层使用的是完整的块设备。这意味着我们不能为每个路径设置每个分区的 I/O 限制。这也意味着当使用可以支持多个块设备映射到指定的路径（带或者不带 RAID）的 ZFS 或 btrfs 时，我们并不知道这个路径是哪个块设备提供的。这意味着，完全有可能，实际上确实有可能，容器使用的多个磁盘挂载点（绑定挂载或直接挂载）可能来自于同一个物理磁盘。这就使限制变得很奇怪。为了使限制生效，LXD 具有猜测给定路径所对应块设备的逻辑，这其中包括询问 ZFS 和 btrfs 工具，甚至可以在发现一个文件系统中循环挂载的文件时递归地找出它们。这个逻辑虽然不完美，但通常会找到一组应该应用限制的块设备。LXD 接着记录并移动到下一个路径。当遍历完所有的路径，然后到了非常奇怪的部分。它会平均你为相应块设备设置的限制，然后应用这些。这意味着你将在容器中“平均”地获得正确的速度，但这也意味着你不能对来自同一个物理磁盘的“/fast”和一个“/slow”目录应用不同的速度限制。 LXD 允许你设置它，但最后，它会给你这两个值的平均值。它怎么工作？除了网络限制是通过较旧但是良好的“tc”实现的，上述大多数限制是通过 Linux 内核的 cgroup API 来实现的。LXD 在启动时会检测你在内核中启用了哪些 cgroup，并且将只应用你的内核支持的限制。如果你缺少一些 cgroup，守护进程会输出警告，接着你的 init 系统将会记录这些。在 Ubuntu 16.04 上，默认情况下除了内存交换审计外将会启用所有限制，内存交换审计需要你通过swapaccount = 1这个内核引导参数来启用。应用这些限制上述所有限制都能够直接或者用某个配置文件应用于容器。容器范围的限制可以使用：lxc config set CONTAINER KEY VALUE 或对于配置文件设置：lxc profile set PROFILE KEY VALUE 当指定特定设备时：lxc config device set CONTAINER DEVICE KEY VALUE 或对于配置文件设置：lxc profile device set PROFILE DEVICE KEY VALUE 有效配置键、设备类型和设备键的完整列表可以看这里。CPU要限制使用任意两个 CPU 核心可以这么做：lxc config set my-container limits.cpu 2 要指定特定的 CPU 核心，比如说第二和第四个：lxc config set my-container limits.cpu 1,3 更加复杂的情况还可以设置范围：lxc config set my-container limits.cpu 0-3,7-11 限制实时生效，你可以看下面的例子：stgraber@dakara:~$ lxc exec zerotier -- cat /proc/cpuinfo | grep ^proces processor : 0 processor : 1 processor : 2 processor : 3 stgraber@dakara:~$ lxc config set zerotier limits.cpu 2 stgraber@dakara:~$ lxc exec zerotier -- cat /proc/cpuinfo | grep ^proces processor : 0 processor : 1 注意，为了避免完全混淆用户空间，lxcfs 会重排 /proc/cpuinfo 中的条目，以便没有错误。就像 LXD 中的一切，这些设置也可以应用在配置文件中：stgraber@dakara:~$ lxc exec snappy -- cat /proc/cpuinfo | grep ^proces processor : 0 processor : 1 processor : 2 processor : 3 stgraber@dakara:~$ lxc profile set default limits.cpu 3 stgraber@dakara:~$ lxc exec snappy -- cat /proc/cpuinfo | grep ^proces processor : 0 processor : 1 processor : 2 要限制容器使用 10% 的 CPU 时间，要设置下 CPU allowance：lxc config set my-container limits.cpu.allowance 10% 或者给它一个固定的 CPU 时间切片：lxc config set my-container limits.cpu.allowance 25ms/200ms 最后，要将容器的 CPU 优先级调到最低：lxc config set my-container limits.cpu.priority 0 内存要直接应用内存限制运行下面的命令：lxc config set my-container limits.memory 256MB （支持的后缀是 KB、MB、GB、TB、PB、EB）要关闭容器的内存交换（默认启用）：lxc config set my-container limits.memory.swap false 告诉内核首先交换指定容器的内存：lxc config set my-container limits.memory.swap.priority 0 如果你不想要强制的内存限制：lxc config set my-container limits.memory.enforce soft 磁盘和块 I/O不像 CPU 和内存，磁盘和 I/O 限制是直接作用在实际的设备上的，因此你需要编辑原始设备或者屏蔽某个具体的设备。要设置磁盘限制（需要 btrfs 或者 ZFS）：lxc config device set my-container root size 20GB 比如：stgraber@dakara:~$ lxc exec zerotier -- df -h / Filesystem Size Used Avail Use% Mounted on encrypted/lxd/containers/zerotier 179G 542M 178G 1% / stgraber@dakara:~$ lxc config device set zerotier root size 20GB stgraber@dakara:~$ lxc exec zerotier -- df -h / Filesystem Size Used Avail Use% Mounted on encrypted/lxd/containers/zerotier 20G 542M 20G 3% / 要限制速度，你可以：lxc config device set my-container root limits.read 30MB lxc config device set my-container root.limits.write 10MB 或者限制 IO 频率：lxc config device set my-container root limits.read 20Iops lxc config device set my-container root limits.write 10Iops 最后你在一个过量使用的繁忙系统上，你或许想要：lxc config set my-container limits.disk.priority 10 将那个容器的 I/O 优先级调到最高。网络 I/O只要机制可用，网络 I/O 基本等同于块 I/O。比如：stgraber@dakara:~$ lxc exec zerotier -- wget http://speedtest.newark.linode.com/100MB-newark.bin -O /dev/null --2016-03-26 22:17:34-- http://speedtest.newark.linode.com/100MB-newark.bin Resolving speedtest.newark.linode.com (speedtest.newark.linode.com)... 50.116.57.237, 2600:3c03::4b Connecting to speedtest.newark.linode.com (speedtest.newark.linode.com)|50.116.57.237|:80... connected. HTTP request sent, awaiting response... 200 OK Length: 104857600 (100M) [application/octet-stream] Saving to: '/dev/null' /dev/null 100%[===================>] 100.00M 58.7MB/s in 1.7s 2016-03-26 22:17:36 (58.7 MB/s) - '/dev/null' saved [104857600/104857600] stgraber@dakara:~$ lxc profile device set default eth0 limits.ingress 100Mbit stgraber@dakara:~$ lxc profile device set default eth0 limits.egress 100Mbit stgraber@dakara:~$ lxc exec zerotier -- wget http://speedtest.newark.linode.com/100MB-newark.bin -O /dev/null --2016-03-26 22:17:47-- http://speedtest.newark.linode.com/100MB-newark.bin Resolving speedtest.newark.linode.com (speedtest.newark.linode.com)... 50.116.57.237, 2600:3c03::4b Connecting to speedtest.newark.linode.com (speedtest.newark.linode.com)|50.116.57.237|:80... connected. HTTP request sent, awaiting response... 200 OK Length: 104857600 (100M) [application/octet-stream] Saving to: '/dev/null' /dev/null 100%[===================>] 100.00M 11.4MB/s in 8.8s 2016-03-26 22:17:56 (11.4 MB/s) - '/dev/null' saved [104857600/104857600] 这就是如何将一个千兆网的连接速度限制到仅仅 100Mbit/s 的！和块 I/O 一样，你可以设置一个总体的网络优先级：lxc config set my-container limits.network.priority 5 获取当前资源使用率LXD API 可以导出目前容器资源使用情况的一点信息，你可以得到：内存：当前、峰值、目前内存交换和峰值内存交换磁盘：当前磁盘使用率网络：每个接口传输的字节和包数。另外如果你使用的是非常新的 LXD（在写这篇文章时的 git 版本），你还可以在lxc info中得到这些信息：stgraber@dakara:~$ lxc info zerotier Name: zerotier Architecture: x86_64 Created: 2016/02/20 20:01 UTC Status: Running Type: persistent Profiles: default Pid: 29258 Ips: eth0: inet 172.17.0.101 eth0: inet6 2607:f2c0:f00f:2700:216:3eff:feec:65a8 eth0: inet6 fe80::216:3eff:feec:65a8 lo: inet 127.0.0.1 lo: inet6 ::1 lxcbr0: inet 10.0.3.1 lxcbr0: inet6 fe80::f0bd:55ff:feee:97a2 zt0: inet 29.17.181.59 zt0: inet6 fd80:56c2:e21c:0:199:9379:e711:b3e1 zt0: inet6 fe80::79:e7ff:fe0d:5123 Resources: Processes: 33 Disk usage: root: 808.07MB Memory usage: Memory (current): 106.79MB Memory (peak): 195.51MB Swap (current): 124.00kB Swap (peak): 124.00kB Network usage: lxcbr0: Bytes received: 0 bytes Bytes sent: 570 bytes Packets received: 0 Packets sent: 0 zt0: Bytes received: 1.10MB Bytes sent: 806 bytes Packets received: 10957 Packets sent: 10957 eth0: Bytes received: 99.35MB Bytes sent: 5.88MB Packets received: 64481 Packets sent: 64481 lo: Bytes received: 9.57kB Bytes sent: 9.57kB Packets received: 81 Packets sent: 81 Snapshots: zerotier/blah (taken at 2016/03/08 23:55 UTC) (stateless) 总结LXD 团队花费了几个月的时间来迭代我们使用的这些限制的语言。 它是为了在保持强大和功能明确的基础上同时保持简单。实时地应用这些限制和通过配置文件继承，使其成为一种非常强大的工具，可以在不影响正在运行的服务的情况下实时管理服务器上的负载。更多信息LXD 的主站在： https://linuxcontainers.org/lxdLXD 的 GitHub 仓库： https://github.com/lxc/lxdLXD 的邮件列表：https://lists.linuxcontainers.orgLXD 的 IRC 频道：#lxcontainers on irc.freenode.net如果你不想在你的机器上安装LXD，你可以在线尝试下。作者简介：我是 Stéphane Graber。我是 LXC 和 LXD 项目的领导者，目前在加拿大魁北克蒙特利尔的家所在的Canonical 有限公司担任 LXD 的技术主管。via: https://www.stgraber.org/2016/03/26/lxd-2-0-resource-control-412/作者：Stéphane Graber 译者：geekpi 校对：wxy本文由 LCTT 组织翻译，Linux中国 荣誉推出
在这个系列的文章中，我们将通过使用 Postfix、Dovecot 和 openssl 这三款工具来为你展示如何在 ubuntu 系统上搭建一个既可靠又易于配置的邮件服务器。在这个容器和微服务技术日新月异的时代，值得庆幸的是有些事情并没有改变，例如搭建一个 Linux 下的邮件服务器，仍然需要许多步骤才能间隔各种服务器耦合在一起，而当你将这些配置好，放在一起，却又非常可靠稳定，不会像微服务那样一睁眼有了，一闭眼又没了。 在这个系列教程中我们将通过使用 Postfix、Dovecot 和 openssl 这三款工具在 ubuntu 系统上搭建一个既可靠又易于配置的邮件服务器。Postfix 是一个古老又可靠的软件，它比原始的 Unix 系统的 MTA 软件 sendmail 更加容易配置和使用（还有人仍然在用sendmail 吗？）。 Exim 是 Debain 系统上的默认 MTA 软件，它比 Postfix 更加轻量而且超级容易配置，因此我们在将来的教程中会推出 Exim 的教程。Dovecot（LCTT 译注：详情请阅读维基百科）和 Courier 是两个非常受欢迎的优秀的 IMAP/POP3 协议的服务器软件，Dovecot 更加的轻量并且易于配置。你必须要保证你的邮件通讯是安全的，因此我们就需要使用到 OpenSSL 这个软件，OpenSSL 也提供了一些很好用的工具来测试你的邮件服务器。为了简单起见，在这一系列的教程中，我们将指导大家安装一个在局域网上的邮件服务器，你应该拥有一个局域网内的域名服务，并确保它是启用且正常工作的，查看这篇“使用 dnsmasq 为局域网轻松提供 DNS 服务”会有些帮助，然后，你就可以通过注册域名并相应地配置防火墙，来将这台局域网服务器变成互联网可访问邮件服务器。这个过程网上已经有很多很详细的教程了，这里不再赘述，请大家继续跟着教程进行即可。一些术语让我们先来快速了解一些术语，因为当我们了解了这些术语的时候就能知道这些见鬼的东西到底是什么。 :DMTA： 邮件传输代理 （ Mail Transfer Agent ） ，基于 SMTP 协议（简单邮件传输协议）的服务端，比如 Postfix、Exim、Sendmail 等。SMTP 服务端彼此之间进行相互通信（LCTT 译注 : 详情请阅读维基百科）。MUA： 邮件用户代理 （ Mail User Agent ） ，你本地的邮件客户端，例如 : Evolution、KMail、Claws Mail 或者 Thunderbird（LCTT 译注 : 例如国内的 Foxmail）。POP3： 邮局协议 （ Post-Office Protocol ） 版本 3，将邮件从 SMTP 服务器传输到你的邮件客户端的的最简单的协议。POP 服务端是非常简单小巧的，单一的一台机器可以为数以千计的用户提供服务。IMAP： 交互式消息访问协议 （ Interactive Message Access Protocol ） ，许多企业使用这个协议因为邮件可以被保存在服务器上，而用户不必担心会丢失消息。IMAP 服务器需要大量的内存和存储空间。TLS： 传输套接层 （ Transport socket layer ） 是 SSL（ 安全套接层 （ Secure Sockets Layer ） ）的改良版，为 SASL 身份认证提供了加密的传输服务层。SASL： 简单身份认证与安全层 （ Simple Authentication and Security Layer ） ，用于认证用户。SASL进行身份认证，而上面说的 TLS 提供认证数据的加密传输。StartTLS: 也被称为伺机 TLS 。如果服务器双方都支持 SSL/TLS，StartTLS 就会将纯文本连接升级为加密连接（TLS 或 SSL）。如果有一方不支持加密，则使用明文传输。StartTLS 会使用标准的未加密端口 25 （SMTP）、 110（POP3）和 143 （IMAP）而不是对应的加密端口 465（SMTP）、995（POP3） 和 993 （IMAP）。啊，我们仍然有 sendmail绝大多数的 Linux 版本仍然还保留着 /usr/sbin/sendmail 。 这是在那个 MTA 只有一个 sendmail 的古代遗留下来的痕迹。在大多数 Linux 发行版中，/usr/sbin/sendmail 会符号链接到你安装的 MTA 软件上。如果你的 Linux 中有它，不用管它，你的发行版会自己处理好的。安装 Postfix使用 apt-get install postfix 来做基本安装时要注意（图 1），安装程序会打开一个向导，询问你想要搭建的服务器类型，你要选择“Internet Server”，虽然这里是局域网服务器。它会让你输入完全限定的服务器域名（例如： myserver.mydomain.net）。对于局域网服务器，假设你的域名服务已经正确配置，(我多次提到这个是因为经常有人在这里出现错误)，你也可以只使用主机名。图 1：Postfix 的配置。Ubuntu 系统会为 Postfix 创建一个配置文件，并启动三个守护进程 : master、qmgr 和 pickup，这里没用一个叫 Postfix 的命令或守护进程。（LCTT 译注：名为 postfix 的命令是管理命令。）$ ps ax 6494 ? Ss 0:00 /usr/lib/postfix/master 6497 ? S 0:00 pickup -l -t unix -u -c 6498 ? S 0:00 qmgr -l -t unix -u 你可以使用 Postfix 内置的配置语法检查来测试你的配置文件，如果没用发现语法错误，不会输出任何内容。$ sudo postfix check [sudo] password for carla: 使用 netstat 来验证 postfix 是否正在监听 25 端口。$ netstat -ant tcp 0 0 0.0.0.0:25 0.0.0.0:* LISTEN tcp6 0 0 :::25 :::* LISTEN 现在让我们再操起古老的 telnet 来进行测试 :$ telnet myserver 25 Trying 127.0.1.1... Connected to myserver. Escape character is '^]'. 220 myserver ESMTP Postfix (Ubuntu) EHLO myserver 250-myserver 250-PIPELINING 250-SIZE 10240000 250-VRFY 250-ETRN 250-STARTTLS 250-ENHANCEDSTATUSCODES 250-8BITMIME 250 DSN ^] telnet> 嘿，我们已经验证了我们的服务器名，而且 Postfix 正在监听 SMTP 的 25 端口而且响应了我们键入的命令。按下 ^] 终止连接，返回 telnet。输入 quit 来退出 telnet。输出的 ESMTP（扩展的 SMTP ） 250 状态码如下。 （LCTT 译注： ESMTP (Extended SMTP)，即扩展 SMTP，就是对标准 SMTP 协议进行的扩展。详情请阅读维基百科）PIPELINING 允许多个命令流式发出，而不必对每个命令作出响应。SIZE 表示服务器可接收的最大消息大小。VRFY 可以告诉客户端某一个特定的邮箱地址是否存在，这通常应该被取消，因为这是一个安全漏洞。ETRN 适用于非持久互联网连接的服务器。这样的站点可以使用 ETRN 从上游服务器请求邮件投递，Postfix 可以配置成延迟投递邮件到 ETRN 客户端。STARTTLS （详情见上述说明）。ENHANCEDSTATUSCODES，服务器支撑增强型的状态码和错误码。8BITMIME，支持 8 位 MIME，这意味着完整的 ASCII 字符集。最初，原始的 ASCII 是 7 位。DSN，投递状态通知，用于通知你投递时的错误。Postfix 的主配置文件是： /etc/postfix/main.cf，这个文件是安装程序创建的，可以参考这个资料来查看完整的 main.cf 参数列表， /etc/postfix/postfix-files 这个文件描述了 Postfix 完整的安装文件。下一篇教程我们会讲解 Dovecot 的安装和测试，然后会给我们自己发送一些邮件。via: https://www.linux.com/learn/how-build-email-server-ubuntu-linux作者：CARLA SCHRODER 译者：WangYihang 校对：wxy本文由 LCTT 组织编译，Linux中国 荣誉推出
这篇文章包括了管理 Samba4 域控制器架构过程中的一些常用命令，比如添加、移除、禁用或者列出用户及用户组等。我们也会关注一下如何配置域安全策略以及如何把 AD 用户绑定到本地的 PAM 认证中，以实现 AD 用户能够在 Linux 域控制器上进行本地登录。要求在 Ubuntu 系统上使用 Samba4 来创建活动目录架构第一步：在命令行下管理1、 可以通过 samba-tool 命令行工具来进行管理，这个工具为域管理工作提供了一个功能强大的管理接口。通过 samba-tool 命令行接口，你可以直接管理域用户及用户组、域组策略、域站点，DNS 服务、域复制关系和其它重要的域功能。使用 root 权限的账号，直接输入 samba-tool 命令，不要加任何参数选项来查看该工具能实现的所有功能。# samba-tool -h samba-tool —— Samba 管理工具2、 现在，让我们开始使用 samba-tool 工具来管理 Samba4 活动目录中的用户。使用如下命令来创建 AD 用户：# samba-tool user add your_domain_user 添加一个用户，包括 AD 可选的一些重要属性，如下所示：--------- review all options --------- # samba-tool user add -h # samba-tool user add your_domain_user --given-name=your_name --surname=your_username --mail-address=your_domain_user@tecmint.lan --login-shell=/bin/bash 在 Samba AD 上创建用户3、 可以通过下面的命令来列出所有 Samba AD 域用户：# samba-tool user list 列出 Samba AD 用户信息4、 使用下面的命令来删除 Samba AD 域用户：# samba-tool user delete your_domain_user 5、 重置 Samba 域用户的密码：# samba-tool user setpassword your_domain_user 6、 启用或禁用 Samba 域用户账号：# samba-tool user disable your_domain_user # samba-tool user enable your_domain_user 7、 同样地，可以使用下面的方法来管理 Samba 用户组：--------- review all options --------- # samba-tool group add –h # samba-tool group add your_domain_group 8、 删除 samba 域用户组：# samba-tool group delete your_domain_group 9、 显示所有的 Samba 域用户组信息：# samba-tool group list 10、 列出指定组下的 Samba 域用户：# samba-tool group listmembers "your_domain group" 列出 Samba 域用户组11、 从 Samba 域组中添加或删除某一用户：# samba-tool group addmembers your_domain_group your_domain_user # samba-tool group remove members your_domain_group your_domain_user 12、 如上面所提到的， samba-tool 命令行工具也可以用于管理 Samba 域策略及安全。查看 samba 域密码设置：# samba-tool domain passwordsettings show 检查 Samba 域密码13、 为了修改 samba 域密码策略，比如密码复杂度，密码失效时长，密码长度，密码重复次数以及其它域控制器要求的安全策略等，可参照如下命令来完成：---------- List all command options ---------- # samba-tool domain passwordsettings -h 管理 Samba 域密码策略不要把上图中的密码策略规则用于生产环境中。上面的策略仅仅是用于演示目的。第二步：使用活动目录账号来完成 Samba 本地认证14、 默认情况下，离开 Samba AD DC 环境，AD 用户不能从本地登录到 Linux 系统。为了让活动目录账号也能登录到系统，你必须在 Linux 系统环境中做如下设置，并且要修改 Samba4 AD DC 配置。首先，打开 Samba 主配置文件，如果以下内容不存在，则添加：$ sudo nano /etc/samba/smb.conf 确保以下参数出现在配置文件中：winbind enum users = yes winbind enum groups = yes Samba 通过 AD 用户账号来进行认证15、 修改之后，使用 testparm 工具来验证配置文件没有错误，然后通过如下命令来重启 Samba 服务：$ testparm $ sudo systemctl restart samba-ad-dc.service 检查 Samba 配置文件是否报错16、 下一步，我们需要修改本地 PAM 配置文件，以让 Samba4 活动目录账号能够完成本地认证、开启会话，并且在第一次登录系统时创建一个用户目录。使用 pam-auth-update 命令来打开 PAM 配置提示界面，确保所有的 PAM 选项都已经使用 [空格] 键来启用，如下图所示：完成之后，按 [Tab] 键跳转到 OK ，以启用修改。$ sudo pam-auth-update 为 Samba4 AD 配置 PAM 认证为 Samba4 AD 用户启用 PAM认证模块17、 现在，使用文本编辑器打开 /etc/nsswitch.conf 配置文件，在 passwd 和 group 参数的最后面添加 winbind 参数，如下图所示：$ sudo vi /etc/nsswitch.conf 为 Samba 服务添加 Winbind Service Switch 设置18、 最后，编辑 /etc/pam.d/common-password 文件，查找下图所示行并删除 user_authtok 参数。该设置确保 AD 用户在通过 Linux 系统本地认证后，可以在命令行下修改他们的密码。有这个参数时，本地认证的 AD 用户不能在控制台下修改他们的密码。password [success=1 default=ignore] pam_winbind.so try_first_pass 允许 Samba AD 用户修改密码在每次 PAM 更新安装完成并应用到 PAM 模块，或者你每次执行 pam-auth-update 命令后，你都需要删除 use_authtok 参数。19、 Samba4 的二进制文件会生成一个内建的 windindd 进程，并且默认是启用的。因此，你没必要再次去启用并运行 Ubuntu 系统官方自带的 winbind 服务。为了防止系统里原来已废弃的 winbind 服务被启动，确保执行以下命令来禁用并停止原来的 winbind 服务。$ sudo systemctl disable winbind.service $ sudo systemctl stop winbind.service 虽然我们不再需要运行原有的 winbind 进程，但是为了安装并使用 wbinfo 工具，我们还得从系统软件库中安装 Winbind 包。wbinfo 工具可以用来从 winbindd 进程侧来查询活动目录用户和组。以下命令显示了使用 wbinfo 命令如何查询 AD 用户及组信息。$ wbinfo -g $ wbinfo -u $ wbinfo -i your_domain_user 检查 Samba4 AD 信息检查 Samba4 AD 用户信息20、 除了 wbinfo 工具外，你也可以使用 getent 命令行工具从 Name Service Switch 库中查询活动目录信息库，在 /etc/nsswitch.conf 配置文件中有相关描述内容。通过 grep 命令用管道符从 getent 命令过滤结果集，以获取信息库中 AD 域用户及组信息。# getent passwd | grep TECMINT # getent group | grep TECMINT 查看 Samba4 AD 详细信息第三步：使用活动目录账号登录 Linux 系统21、 为了使用 Samba4 AD 用户登录系统，使用 su - 命令切换到 AD 用户账号即可。第一次登录系统后，控制台会有信息提示用户的 home 目录已创建完成，系统路径为 /home/$DOMAIN/ 之下，名字为用户的 AD 账号名。使用 id 命令来查询其它已登录的用户信息。# su - your_ad_user $ id $ exit 检查 Linux 下 Samba4 AD 用户认证结果22、 当你成功登入系统后，在控制台下输入 passwd 命令来修改已登录的 AD 用户密码。$ su - your_ad_user $ passwd 修改 Samba4 AD 用户密码23、 默认情况下，活动目录用户没有可以完成系统管理工作的 root 权限。要授予 AD 用户 root 权限，你必须把用户名添加到本地 sudo 组中，可使用如下命令完成。确保你已输入域 、斜杠和 AD 用户名，并且使用英文单引号括起来，如下所示：# usermod -aG sudo 'DOMAIN\your_domain_user' 要检查 AD 用户在本地系统上是否有 root 权限，登录后执行一个命令，比如，使用 sudo 权限执行 apt-get update 命令。# su - tecmint_user $ sudo apt-get update 授予 Samba4 AD 用户 sudo 权限24、 如果你想把活动目录组中的所有账号都授予 root 权限，使用 visudo 命令来编辑 /etc/sudoers 配置文件，在 root 权限那一行添加如下内容：%DOMAIN\\your_domain\ group ALL=(ALL:ALL) ALL 注意 /etc/sudoers 的格式，不要弄乱。/etc/sudoers 配置文件对于 ASCII 引号字符处理的不是很好，因此务必使用 '%' 来标识用户组，使用反斜杠来转义域名后的第一个斜杠，如果你的组名中包含空格（大多数 AD 内建组默认情况下都包含空格）使用另外一个反斜杠来转义空格。并且域的名称要大写。授予所有 Samba4 用户 sudo 权限好了，差不多就这些了！管理 Samba4 AD 架构也可以使用 Windows 环境中的其它几个工具，比如 ADUC、DNS 管理器、 GPM 等等，这些工具可以通过安装从 Microsoft 官网下载的 RSAT 软件包来获得。要通过 RSAT 工具来管理 Samba4 AD DC ，你必须要把 Windows 系统加入到 Samba4 活动目录。这将是我们下一篇文章的重点，在这之前，请继续关注。via: http://www.tecmint.com/manage-samba4-active-directory-linux-command-line作者：Matei Cezar 译者：rusking 校对：wxy本文由 LCTT 原创编译，Linux中国 荣誉推出
经常有人问哪个编程语言最流行？这问题很简单，但是回答起来可没那么简单。首先，我们要知道，为什么人们会问这样的问题？一般问这样的问题是人大多是学生，他们想知道这个问题的答案是因为他们想要找份工作，所以寻求一种可以增加面试成功率的技能。对于大多数人来说，进入一个新的领域时了解什么是最流行的，是很有意义的。而对于其他人来说，比如说已经掌握了一种或几种编程语言的程序员，他可能在想要掌握一门新的编程语言时，会考虑一下当前最流行的编程语言作为参考。而对于要开发一个产品的程序员来说，也希望了解当前最流行的编程语言是因为他们希望所开发的产品能够迎合客户的环境和需求，显然支持流行的语言的 API 会被更多人使用。甚至，就算是你想启动一个项目时，你也需要考虑是否选择一个流行的编程语言。虽然你首先要考虑的是这种语言能够满足你的需求，比如说如果用一个流行的编程语言你需要花费更多的时间和成本，而不那么流行的编程语言或许会更快捷和轻松，显然你还是会选择那个不太流行的——但是如果各个方面都差不多，不用说你会选择流行的那个，因为这样你可以找到更多的程序员，遇到问题也有更多的解决方案。怎么才算是流行？那么，哪个语言是最流行的？其实回答这个问题并没有你想象的那么简单。关键是，你该怎么定义这个“流行”？这个问题并没有固定的答案，不过在维基上有一篇文章提到了如何测量编程语言的流行度。在这篇文章中，列出了几个测量流行度的因素：该语言在搜索中提及的次数，比如在谷歌趋势中在招聘广告中提及该语言的次数传授和介绍该语言的书籍销售量以该语言编写的现存代码的行数，不流行的语言在公开搜索中可能根本就找不到在 GitHub、Freecode 上使用该语言的项目数量在论坛和新闻组中讨论该语言的帖子数量此外，你还可以考量如下指标：编程培训班里面该语言的培训课程销售数量编程培训班里面学生的数量视频网站里面关于该语言的视频数量Stack Overflow 和 Reddit 里面关于该语言的帖子数量甚至，你还可以增加一些其它的统计维度，比如根据国家和城市来统计，你知道在北京哪种编程语言最流行么？上海呢？所以，这个问题的回答并不是一个简单的答案。统计数据来源的不同即使我们知道了流行度取决于多种因素，但是人们还是希望能够了解到底哪个语言比较流行，以此来指导他们的培训和公司的决策。有一些网站依据不同的标准，公开发布了一些语言流行度指标。 IEEE Spectrum 对这些指标做了一个有趣的整合，它可以让你通过自行设置不同因子的权重来得到你自己的编程语言流行度排行榜。Coding Dojo 也有一个图表，聚合了工作搜索引擎 Indeed.com 的数据；而有名的 Tiobe 排行榜一直使用搜索引擎聚合来计算流行度； PyPl 则是根据谷歌来查看语言的流行度。 然而，这并没什么大用。如果你想知道你该学习那种语言，或者是你需要支持的语言，最困难的还是你并不知道这里的哪个图表才是适合你的。好吧，我明白了，那么到底那种编程语言是流行的？为了帮助你找到方向，我组合了上述提及的几种数据源，包括三种 IEEE 分类：“趋势”代表语言的增长度，“工作”代表 Dice.com 和 CareerBuilder 上的招聘量，“开源”代表开源项目数量。排名结果如下表： 但是问题是，上图并不能告诉我们重点所在。要解决这个问题，我们需要做一点数据分析。我聚合了这六个数据源中的五个（我去掉了 Coding Dojo 是因为它仅显示了前九），然后我根据编程语言出现在图表中的位置和次数进行加权，这样我得到了如下的前十排名。如你所见，这些语言分成了三大类。第一梯队包括 Java、C、Python 和 C++，毫无疑问，你肯定经常听到它们的名字。第二梯队包括 JavaScript、C#、PHP 和 Swift。剩下的两个是 Objective-C 和 R。这给我们带来什么启发？第一梯队的语言 Java、C、Python 和 C++ 都是非常通用的语言，它们并不局限于特定的编程平台或用途。最值得关注的是第二梯队，它包括 JavaScript、C#、PHP 和 Swift。JavaScript 和 PHP 是主要的 Web 开发语言。C# 是微软的编程语言，而 Swift 是苹果新推出的主力语言。基本上来说，第二梯队是平台相关的。那么这反映了什么？如果你懂一点现代编程，你就知道编程其实不仅仅是使用这种语言，而更重要的是开发一些什么，比如说嵌入式系统、iPhone 应用、Web 应用或者微软的服务器端应用等等。对语言的熟悉程度其实只是一小部分。举个例子说，不管你是多么的喜欢 Python 或者古老而常青的 C，但如果你要为 WordPress 开发插件或主题，你只能使用 JavaScript 和 PHP。这无关于哪个语言更流行。字里行间的发现或者你会注意到一些有趣的地方。首先，Coding Dojo 的编程语言排行榜的第一名是 SQL，只有它一家是这样。你很少会单独在 SQL 里面编程，通常都是在其它的语言里面使用它来管理数据。所以，学会 SQL 是很有用的，甚至是必要的。然而，去上一门 SQL 的培训课程并不能帮你找到一份工作，也不会多挣多少钱。其次，苹果特有的语言在排行榜中排名很低，这或许和你的预期不同，因为 iOS 的应用是如此的流行。不过确实是这样的，如果你不是要开发你自己的应用的话，那学它们其实不如学习别的语言，因为其实没有那么多的公司雇佣苹果应用开发人员。这就是 Swift 语言掉到了榜尾的原因，而 Objective-C 正在被 Swift 所替代，在前面也看到了它也处于榜单的后面。C 家族的语言仍然是主流。Java、C++、C、C#，甚至 Objective-C 都是基于 C 的语言。如果你只想学一门语言，你可以从其中选择一个。我推荐你选择 Java 或 C++，它们可以为你打开进入 C 语言家族的大门。以我的职业生涯的经验来看，不是特别复杂的场景的话，我大概能用 20 来种语言来编程，通常我只用几天就可以学会一门新的语言。这是因为我在学校的专业就是语言设计，我也教编程超过了 20 年了。掌握这么多的语言对我很有帮助，因为我总是根据我要做的事情选择一种语言，而不是专门去上课学习一种语言。这听起来好像有点难，但是其实你也能做到的。我的建议就是，如果你要编程，那么就去学习多种编程语言和各种框架吧。用编程语言去做点东西出来，编程不仅仅是一种智力锻炼，而且你可以实际用它做点什么出来。掌握多种语言和框架是重要的，因为计算机行业变得太快了。C 语言依然历久弥新，而 Swift 虽然出现才几年就登上了排行榜。你今天学习到的或许不够你整个职业生涯挥霍，所以“怎样学习语言”要比“学习语言”更重要，最好的办法就是多学几门。我的推荐非常简单，无论是 C++ 还是 Java，选一个学习就好了。然后是 JavaScript，越来越多的基于 Web 的应用需要良好的 JavaScript 技能。再然后是 PHP、Swift 或 Python 中选一个，这要看你的工作种类了。当你在这三个梯队中都学会一门后，你就可以根据你的情况学习更多的语言和框架了。好了，努力吧，学习一些编程语言，做点漂亮的成绩出来。如果你有什么想法，欢迎在下面和我们分享。