# Raspberry Pi и программирование на Go Go или GoLang - компилируемый язык программирования разработанный Google. Go широко используется для web разработки и на сегодня это самый быстро растущий язык. В отличии от Java который запускается в JVM, Go собирается прямо в Windows, OS X or Linux исполняемые файлы. В этой статье мы взглянем на создание двух програм, которые разговаривают с Raspberry Pi GPIO. Первая будет просто клавиатурный ввод программы, а вторая будет отдельным web приложением управляюищим пинами GPIO. # Raspberry Pi GPIO Есть можество различных способов производить подключение к GPIO. Для нашего примера мы собираемся посмотреть на вывод gpio терминальной утилиты, так же будем использовать go-rpi библиотеку. Для тестирования мне нравится использовать gpio утилиту так как она предлагает хороший выбор команд и я могу в ручном режиме протестировать и проверить команды, прежде, чем я буду использовать их в коде. Для помощи можно воспользоваться ключем `-h`. Аппаратное обеспечение Raspberry PI настраивается используя резистор на физическом пине 7(BCM пин 4) [![Led_setu](https://notepad.gasick.ru/uploads/images/gallery/2021-10/scaled-1680-/image-1634905026104.png)](https://notepad.gasick.ru/uploads/images/gallery/2021-10/image-1634905026104.png) Наша первая программа(keyin.go) будет читать ввод клавиатуры и затем направлять в gpio дважды, первый раз, чтобы записать значение, второй раз чтобы прочитать значение обратно. ```go package main import ( "bufio" "fmt" "os/exec" "os" ) func main() { // Get keyboard input reader := bufio.NewReader(os.Stdin) fmt.Print("Enter value for GPIO pin 7 : ") pinval, _ := reader.ReadString('\n') // Write to GPIO pin 7 using keyboard input testCmd := exec.Command("gpio","write", "7", pinval) testOut, err := testCmd.Output() if err != nil { println(err) } // Read back the GPIO pin 7 status testCmd = exec.Command("gpio","read", "7") testOut, err = testCmd.Output() if err != nil { println(err) } else { fmt.Print("GPIO Pin 4 value : ") fmt.Println(string(testOut)) } } ``` Скомпилируем и запустим keyin.go программу: ```bash $ go build keyin.go $ ./keyin Enter value for GPIO pin 7 : 1 GPIO Pin 4 value : 1 ``` # Простое Go веб-приложение Для начального примера мы сделаем веб-приложение(web_static.go) которое показывает страничку `web_static.html`. web_static.html выглядит следующим образом: ```html GO PI Static Page

GO PI Static Page


This is a static test page ``` `web_static.go` программе необходимо импортировать `net/http` библиотеку. `http.HandleFunc` вызов используется для стандартного адреса “/” и раздачи с помощью сервера нашего `web_static.html` файла. `http.ListenAndServe` фукнция слушает web запросы на порту 8081. ```go package main import ( "log" "net/http" ) func main() { // Create default web handler, and call a starting web page http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { http.ServeFile(w, r, "web_static.html") println("Default Web Page") }) // start a listening on port 8081 log.Fatal(http.ListenAndServe("8081", nil)) } ``` Go код может быть скомпилирован и запущен. ```bash $ go build web_static.go $ ./web_static Default Web Page ``` Из web бразуера указывающего на Raspberry Pi и порт 8081,наше приложение будет выглядит так: [![web_static](https://notepad.gasick.ru/uploads/images/gallery/2021-10/scaled-1680-/image-1634904998928.png)](https://notepad.gasick.ru/uploads/images/gallery/2021-10/image-1634904998928.png) # Go Web приложение с Pi GPIO Следующий шаг - создание web страницы которая может передавать параметры. Для этогоп риложения мы переключим GPIO вывод с `on` на `off`. Новая web страница(go_buttons.html) создается с двумя кнопками. Html якорь используется для передачи `/on` и `/off` параметров в наше web приложение. `CACHE-CONTROL` тег устанавливается в `NO-CACHE` для того, чтобы мы точно знали, что страница перезагружается. Я так же включил `EXPIRES` тег равным нулю, чтобы браузер всегда видел страничку "испорченной". Если вы не включаете их то страница может быт загружена только один раз. ```html GO PI GPIO

Go Raspberry Pi GPIO Test


``` Наше новое web приложение(go_buttons.go) теперь включает еще две `http.HandleFunc` функции обработчика, одну для `/on` и одну для `/off`. Эти обработчики вызывают функцию которая вызывает gpio, что используется для написания вывода и чтения обратно статуса ввода. Наша новоиспеченная gpio функция выполняет ходит 2 раза к gpio командной утилите, первый раз записать значение, второй - прочитать значение обратно. ```go package main import ( "log" "net/http" "os/exec" ) func gpio( pinval string) { testCmd := exec.Command("gpio","write", "7", pinval) testOut, err := testCmd.Output() if err != nil { println(err) } testCmd = exec.Command("gpio","read", "7") testOut, err = testCmd.Output() if err != nil { println(err) } else { print("GPIO Pin 4 value : ") println(string(testOut)) } } func main() { http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { http.ServeFile(w, r, "go_buttons.html") println("Default Web Page") }) http.HandleFunc("/on", func(w http.ResponseWriter, r *http.Request) { http.ServeFile(w, r, "go_buttons.html") println("Web Page sent : ON") gpio("1") }) http.HandleFunc("/off", func(w http.ResponseWriter, r *http.Request) { http.ServeFile(w, r, "go_buttons.html") println("Web Page sent : OFF") gpio("0") }) log.Fatal(http.ListenAndServe(":8081", nil)) } ``` Скомпилируем и запустим go_buttons: ```bash $ go build go_buttons.go $ ./go_buttons Default Web Page Web Page sent : ON GPIO Pin 4 value : 1 Default Web Page Web Page sent : OFF GPIO Pin 4 value : 0 ``` The web page should look something like: [![](https://notepad.gasick.ru/uploads/images/gallery/2021-10/scaled-1680-/image-1634904977872.png)](https://notepad.gasick.ru/uploads/images/gallery/2021-10/image-1634904977872.png) # Выводы Для конечного приложения я бы предпочёл использовать Go нативную библиотеку для вызовов GPIO, но для прототипирования я нашел, что командная утилита проще в решении проблем.