Open-source News

Fedora 38 Cleared To Ship With Its Bleeding Edge Compiler Toolchain

Phoronix - Mon, 01/30/2023 - 19:48
Last week the Fedora Engineering and Steering Committee (FESCo) signed off on Fedora 38 shipping with its planned bleeding-edge compiler toolchain, most notably including the upcoming GCC 13 compiler...

labwc 0.6.1 Released For Window-Stacking Wayland Compositor

Phoronix - Mon, 01/30/2023 - 19:31
Labwc that has been in development for a few years as a window-stacking Wayland compositor issued its latest release this weekend...

Unvanquished 0.54 Brings More Renderer Improvements, ARM Binaries

Phoronix - Mon, 01/30/2023 - 19:21
Unvanquished 0.54 was released overnight as the latest update across the array of many releases going back a decade for this open-source first person shooter game. With Unvanquished 0.54 there continues to be enhancements to its renderer, the project is now providing ARM binaries on Linux to complement their x86/x86_64 builds, user-interface improvements, and gameplay enhancements...

How to use GitOps to automate Terraform

opensource.com - Mon, 01/30/2023 - 16:00
How to use GitOps to automate Terraform robstr Mon, 01/30/2023 - 03:00

GitOps as a workflow is perfect for application delivery, mostly used in Kubernetes environments, but it is also possible to use for infrastructure. In a typical GitOps scenario, you might want to look at solutions like Crossplane as a Kubernetes-native alternative, while most traditional infrastructure are still used with CI/CD pipelines. There are several benefits of creating your deployment platform with Kubernetes as the base, but it also means that more people would have to have that particular skill set. One of the benefits of an Infrastructure-as-Code tool like Terraform is that it is easy to learn, and doesn't require much specialized knowledge.

When my team was building our platform services, we wanted everyone to be able to contribute. Most, if not all, of our engineers use Terraform on a daily basis. They know how to create Terraform modules that can be used in several scenarios and for several customers. While there are several ways of automating Terraform, we would like to utilize a proper GitOps workflow as much as possible.

How does the Terraform controller work

While searching for alternatives for running Terraform using Kubernetes, I found several controllers and operators, but none that I felt had as much potential as the tf-controller from Weaveworks. We are already using Flux as our GitOps tool. The tf-controller works by utilizing some of the core functionality from Flux, and has a custom resource for Terraform deployments. The source controller takes care of fetching our modules, the Kustomize controllers apply the Terraform resources, and then the controller spins up static pods (called runners) that run your Terraform commands.

The Terraform resource looks something like this:

apiVersion: infra.contrib.fluxcd.io/v1alpha1 kind: Terraform metadata: name: helloworld namespace: flux-system spec: interval: 1m approvePlan: auto path: ./terraform/module sourceRef: kind: GitRepository name: helloworld namespace: flux-system

There are a few things to note on the specs here. The interval in the spec controls how often the controller starts up the runner pods. This then performs a terraform plan on your root module, which is defined by the path parameter.

This particular resource is set to automatically approve a plan. This means that if there is a difference between the plan and the current state of the target system, a new runner will run to apply the changes automatically. This makes the process as "GitOps" as possible, but you can disable this. If you disable it, you have to manually approve plans. You can do this either by using the Terraform Controller CLI or by updating your manifests with a reference to the commit which should be applied. For more details, see the documentation on manual approval.

The tf-controller utilizes the source controller from Flux. The sourceRef attribute is used to define which source resource you want to use, just like a Flux Kustomization resource would.

Advanced deployments

While the example above works, it's not the type of deployment my team would normally do. When not defining a backend storage, the state would get stored in the cluster, which is fine for testing and development. But for production, I prefer that the state file is stored somewhere outside the cluster. I don't want this defined in the root module directly, as I want to reuse our root modules in several deployments. This means I have to define our backend in our Terraform resource.

Here is an example of how I set up custom backend configurations. You can find all available backends in the Terraform docs:

apiVersion: infra.contrib.fluxcd.io/v1alpha1 kind: Terraform metadata: name: helloworld namespace: flux-system spec: backendConfig: customConfiguration: | backend "azurerm" { resource_group_name = "rg-terraform-mgmt" storage_account_name = "stgextfstate" container_name = "tfstate" key = "helloworld.tfstate" } ...

Storing the state file outside the cluster means that I can redeploy our cluster. But then there is no storage dependency. There is no need for backup or state migration. As soon as the new cluster is up, it runs the commands against the same state, and I am back in business.

Another advanced move is dependencies between modules. Sometimes we design deployments like a two-stage rocket, where one deployment sets up certain resources that the next one uses. In these scenarios, we need to make sure that our Terraform is written in such a fashion so that we output any data needed as inputs for the second module, and ensure that the first module has a successful run first.

These two examples are from code used while demonstrating dependencies, and all the code can be found on my GitHub. Some of the code is omitted for brevity's sake:

apiVersion: infra.contrib.fluxcd.io/v1alpha1 kind: Terraform metadata: name: shared-resources namespace: flux-system spec: ... writeOutputsToSecret: name: shared-resources-output ... apiVersion: infra.contrib.fluxcd.io/v1alpha1 kind: Terraform metadata: name: workload01 namespace: flux-system spec: ... dependsOn: - name: shared-resources ... varsFrom: - kind: Secret name: shared-resources-output ...

In the deployment that I call shared-resources, you see that I defined a secret where the outputs from the deployment should be stored. In this case, the outputs are the following:

output "subnet_id" { value = azurerm_virtual_network.base.subnet.*.id[0] } output "resource_group_name" { value = azurerm_resource_group.base.name }

In the workload01 deployment, I first define our dependency with the dependsOn attribute, which makes sure that shared-resources has a successful run before scheduling workload01. The outputs from shared-resources is then used as inputs in workload01, which is the reason why I want to wait.

More on automation Download now: The automated enterprise eBook Free online course: Ansible essentials Ansible cheat sheet eBook: A practical guide to home automation using open source tools A quickstart guide to Ansible eBook: 7 examples of automation on the edge More articles about open source automation Why not pipelines or Terraform Cloud

The most common approach to automating Terraform is either by using CI/CD pipelines or Terraform Cloud. Using pipelines for Terraform works fine, but usually ends up with needing to copy pipeline definitions over and over again. There are solutions to that, but by using the tf-controller you have a much more declarative approach to defining what you want your deployments to look like rather than defining the steps in an imperative fashion.

Terraform Cloud has introduced a lot of features that overlap with using the GitOps workflow, but using the tf-controller does not exclude you from using Terraform Cloud. You could use Terraform Cloud as the backend for your deployment, only automating the runs through the tf-controller.

The reason that my team uses this approach is that we already deploy applications using GitOps, and we have much more flexibility as to how we can offer these capabilities as a service. We can control our implementation through APIs, making self-service more accessible to both our operators and end-users. The details around our platform approach are such a big topic, that we will have to return to those in its own article.

This article was originally published on the author's blog and has been republished with permission.

Instead of using CI/CD pipelines or Terraform Cloud, try this alternative approach to automating Terraform using Flux and GitOps.

Image by:

opensource.com

CI/CD Automation Kubernetes What to read next This work is licensed under a Creative Commons Attribution-Share Alike 4.0 International License. Register or Login to post a comment.

Learn to code a simple game in Zig

opensource.com - Mon, 01/30/2023 - 16:00
Learn to code a simple game in Zig Moshe Zadka Mon, 01/30/2023 - 03:00

Writing the same application in multiple languages is a great way to learn new ways to program. Most programming languages have certain things in common, such as:

  • Variables
  • Expressions
  • Statements

These concepts are the basis of most programming languages. Once you understand them, you can take the time you need to figure out the rest.

Furthermore, programming languages usually share some similarities. Once you know one programming language, you can learn the basics of another by recognizing its differences.

A good tool for learning a new language is by practicing with a standard program.
This allows you to focus on the language, not the program's logic. I'm doing that in this article series using a "guess the number" program, in which the computer picks a number between 1 and 100 and asks you to guess it. The program loops until you guess the number correctly.

This program exercises several concepts in programming languages:

  • Variables
  • Input
  • Output
  • Conditional evaluation
  • Loops

It's a great practical experiment to learn a new programming language.

Guess the number in Zig basic

Zig is still in the alpha stage, and subject to change. This article is correct as of zig version 0.11. Install zig by going to the downloads directory and downloading the appropriate version for your operating system and architecture:

const std = @import("std"); fn ask_user() !i64 { const stdin = std.io.getStdIn().reader(); const stdout = std.io.getStdOut().writer(); var buf: [10]u8 = undefined; try stdout.print("Guess a number between 1 and 100: ", .{}); if (try stdin.readUntilDelimiterOrEof(buf[0..], '\n')) |user_input| { return std.fmt.parseInt(i64, user_input, 10); } else { return error.InvalidParam; } } pub fn main() !void { const stdout = std.io.getStdOut().writer(); var prng = std.rand.DefaultPrng.init(blk: { var seed: u64 = undefined; try std.os.getrandom(std.mem.asBytes(&seed)); break :blk seed; }); const value = prng.random().intRangeAtMost(i64, 1, 100); while (true) { const guess = try ask_user(); if (guess == value) { break; } const message = if (guess < value) "low" else "high"; try stdout.print("Too {s}\n", .{message}); } try stdout.print("That's right\n", .{}); }

The first line const std = @import("std"); imports the Zig standard library.
Almost all programs will need it.

The ask_user function in Zig

The function ask_user() returns a 64-bit integer or an error. This is what the ! (exclamation mark) notes. This means if there is an I/O issue or the user enters an invalid input, the function returns an error.

The try operator calls a function and return its value. If it returns an error, it immediately returns from the calling function with an error. This allows explicit, but easy, error propagation. The first two lines in ask_user alias contains some constants from std.
This makes the following I/O code simpler.

This line prints the prompt:

try stdout.print("Guess a number between 1 and 100: ", .{});

It automatically returns a failure if the print fails (for example, writing to a closed terminal).

This line defines the buffer into which user input is read:

var buf: [10]u8 = undefined;

The expression inside the if clause reads user input into the buffer:

(try stdin.readUntilDelimiterOrEof(buf[0..], '\n')) |user_input|

The expression returns the slice of the buffer that was read into. This is assigned to the variable user_input, which is only valid inside the if block.

The function std.fmt.parseInt returns an error if the number cannot be parsed.
This error is propagated to the caller. If no bytes have been read, the function immediately returns an error.

Programming and development Red Hat Developers Blog Programming cheat sheets Try for free: Red Hat Learning Subscription eBook: An introduction to programming with Bash Bash shell scripting cheat sheet eBook: Modernizing Enterprise Java An open source developer's guide to building applications The main function

The function begins by getting a random number. It uses std.rand.DefaultPrng.

The function initializes the random number generator with std.os.getrandom. It then uses the generator to get a number in the range of 1 to 100.

The while loop continues while true is true, which is forever. The only way out is with the break, which happens when the guess is equal to the random value.

When the guess is not equal, the if statement returns the string low or high depending on the guess. This is interpolated into the message to the user.

Note that main is defined as !void, which means it can also return an error. This allows using the try operator inside main.

Sample output

An example run, after putting the program in main.zig:

$ zig run main.zig Guess a number between 1 and 100: 50 Too high Guess a number between 1 and 100: 25 Too low Guess a number between 1 and 100: 37 Too low Guess a number between 1 and 100: 42 Too high Guess a number between 1 and 100: 40 That's rightSummary

This "guess the number" game is a great introductory program for learning a new programming language because it exercises several common programming concepts in a pretty straightforward way. By implementing this simple game in different programming languages, you can demonstrate some core concepts of the languages and compare their details.

Do you have a favorite programming language? How would you write the "guess the number" game in it? Follow this article series to see examples of other programming languages that might interest you!

Practice programming in Zig by writing a "guess the number" game.

Image by:

Ray Smith

Programming What to read next This work is licensed under a Creative Commons Attribution-Share Alike 4.0 International License. Register or Login to post a comment.

9 Best Google Drive Clients for Linux in 2023

Tecmint - Mon, 01/30/2023 - 14:53
The post 9 Best Google Drive Clients for Linux in 2023 first appeared on Tecmint: Linux Howtos, Tutorials & Guides .

One of the best cloud storage contenders to emerge is Google Drive – the popular cloud storage application that allows you to store data and access it from a Google account securely. Unfortunately, despite

The post 9 Best Google Drive Clients for Linux in 2023 first appeared on Tecmint: Linux Howtos, Tutorials & Guides.

GIMP 3.0 Aiming To Release In 2023

Phoronix - Mon, 01/30/2023 - 13:00
The long elusive GIMP 3.0 release that overhauls the UI and ports from GTK2 to GTK3 along with a wealth of other changes after being talked about for a decade could finally see its stable release this year...

Unlock your business potential with open leadership

Red Hat News - Mon, 01/30/2023 - 08:00
<p>When a leader of any kind begins to take on transforming or modernizing their business, whether it’s a small team or an entire organization, it requires change in multiple directions. What was successful in the past might not work in the changing volatile, uncertain, complex and ambiguous (VUCA) world anymore. Leadership can be practiced at every level of an organization irrespective of the role, title or position, by both people managers and individual contributors alike. Leadership is not the same thing as management,especially in organizations using open leadership, where

Linux 6.2-rc6 Released & It's Suspiciously Small

Phoronix - Mon, 01/30/2023 - 06:50
Linus Torvalds just released the sixth weekly RC of Linux 6.2 and it's coming in unusually light...

Budgie 10.7 Released With Big Improvements To This Linux Desktop

Phoronix - Mon, 01/30/2023 - 05:31
Budgie 10.7 is out today as the newest feature release to this open-source desktop environment that was originally developed as part of the Solus Linux distribution...

Pages