Skip to content

Instantly share code, notes, and snippets.

@pmarkun
Created October 23, 2014 17:55
Show Gist options
  • Select an option

  • Save pmarkun/78d41548ec9d87195ba6 to your computer and use it in GitHub Desktop.

Select an option

Save pmarkun/78d41548ec9d87195ba6 to your computer and use it in GitHub Desktop.
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=0">
<title>APIs - Hackathon SESI Cultura Digital</title>
<style type="text/css">
body {
font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif;
color: #222;
background-color: #f7f7f7;
font-size: 100%;
}
.slide {
position: absolute;
top: 0; bottom: 0;
left: 0; right: 0;
}
.slide-content {
width: 800px;
height: 600px;
overflow: hidden;
margin: 80px auto 0 auto;
padding: 30px;
font-weight: 200;
font-size: 200%;
line-height: 1.375;
}
.controls {
position: absolute;
bottom: 20px;
left: 20px;
}
.arrow {
width: 0; height: 0;
border: 30px solid #333;
float: left;
margin-right: 30px;
-webkit-touch-callout: none;
-webkit-user-select: none;
-khtml-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
}
.prev {
border-top-color: transparent;
border-bottom-color: transparent;
border-left-color: transparent;
border-left-width: 0;
border-right-width: 50px;
}
.next {
border-top-color: transparent;
border-bottom-color: transparent;
border-right-color: transparent;
border-left-width: 50px;
border-right-width: 0;
}
.prev:hover {
border-right-color: #888;
cursor: pointer;
}
.next:hover {
border-left-color: #888;
cursor: pointer;
}
h1 {
font-size: 300%;
line-height: 1.2;
text-align: center;
margin: 170px 0 0;
}
h2 {
font-size: 100%;
line-height: 1.2;
margin: 5px 0;
text-align: center;
font-weight: 200;
}
h3 {
font-size: 140%;
line-height: 1.2;
border-bottom: 1px solid #aaa;
margin: 0;
padding-bottom: 15px;
}
ul {
padding: 20px 0 0 60px;
font-weight: 200;
line-height: 1.375;
}
.author h1 {
font-size: 170%;
font-weight: 200;
text-align: center;
margin-bottom: 30px;
}
.author h3 {
font-weight: 100;
text-align: center;
font-size: 95%;
border: none;
}
a {
text-decoration: none;
color: #44a4dd;
}
a:hover {
color: #66b5ff;
}
pre {
font-size: 60%;
line-height: 1.3;
}
.progress {
position: fixed;
top: 0; left: 0; right: 0;
height: 3px;
}
.progress-bar {
width: 0%;
height: 3px;
background-color: #b4b4b4;
-webkit-transition: width 0.05s ease-out;
-moz-transition: width 0.05s ease-out;
-o-transition: width 0.05s ease-out;
transition: width 0.05s ease-out;
}
.hidden {
display: none;
}
@media (max-width: 850px) {
body {
font-size: 70%;
}
.slide-content {
width: auto;
}
img {
width: 100%;
}
h1 {
margin-top: 120px;
}
.prev, .prev:hover {
border-right-color: rgba(135, 135, 135, 0.5);
}
.next, .next:hover {
border-left-color: rgba(135, 135, 135, 0.5);
}
}
@media (max-width: 480px) {
body {
font-size: 50%;
overflow: hidden;
}
.slide-content {
padding: 10px;
margin-top: 10px;
height: 340px;
}
h1 {
margin-top: 50px;
}
ul {
padding-left: 25px;
}
}
@media print {
* {
-webkit-print-color-adjust: exact;
}
@page {
size: letter;
}
.hidden {
display: inline;
}
html {
width: 100%;
height: 100%;
overflow: visible;
}
body {
margin: 0 auto !important;
border: 0;
padding: 0;
float: none !important;
overflow: visible;
background: none !important;
font-size: 52%;
}
.progress, .controls {
display: none;
}
.slide {
position: static;
}
.slide-content {
border: 1px solid #222;
margin-top: 0;
margin-bottom: 40px;
height: 3.5in;
overflow: visible;
}
.slide:nth-child(even) {
/* 2 slides per page */
page-break-before: always;
}
}
/*
github.com style (c) Vasily Polovnyov <vast@whiteants.net>
*/
code, pre {
border: 1px solid #ddd;
border-radius: 3px;
overflow: auto;
padding: 6px 10px;
}
code {
padding: 0 5px;
}
pre>code {
margin: 0; padding: 0;
border: none;
background: transparent;
}
pre .comment,
pre .template_comment,
pre .diff .header,
pre .javadoc {
color: #998;
font-style: italic
}
pre .keyword,
pre .css .rule .keyword,
pre .winutils,
pre .javascript .title,
pre .nginx .title,
pre .subst,
pre .request,
pre .status {
color: #333;
font-weight: bold
}
pre .number,
pre .hexcolor,
pre .ruby .constant {
color: #099;
}
pre .string,
pre .tag .value,
pre .phpdoc,
pre .tex .formula {
color: #d14
}
pre .title,
pre .id {
color: #900;
font-weight: bold
}
pre .javascript .title,
pre .lisp .title,
pre .clojure .title,
pre .subst {
font-weight: normal
}
pre .class .title,
pre .haskell .type,
pre .vhdl .literal,
pre .tex .command {
color: #458;
font-weight: bold
}
pre .tag,
pre .tag .title,
pre .rules .property,
pre .django .tag .keyword {
color: #000080;
font-weight: normal
}
pre .attribute,
pre .variable,
pre .lisp .body {
color: #008080
}
pre .regexp {
color: #009926
}
pre .class {
color: #458;
font-weight: bold
}
pre .symbol,
pre .ruby .symbol .string,
pre .lisp .keyword,
pre .tex .special,
pre .prompt {
color: #990073
}
pre .built_in,
pre .lisp .title,
pre .clojure .built_in {
color: #0086b3
}
pre .preprocessor,
pre .pi,
pre .doctype,
pre .shebang,
pre .cdata {
color: #999;
font-weight: bold
}
pre .deletion {
background: #fdd
}
pre .addition {
background: #dfd
}
pre .diff .change {
background: #0086b3
}
pre .chunk {
color: #aaa
}
</style>
</head>
<body>
<div class="progress">
<div class="progress-bar"></div>
</div>
<div class="slide" id="slide-1">
<section class="slide-content"><h1 id="apis-101">APIs 101</h1>
<h2 id="the-good-the-bad-the-ugly">The good, the bad, the ugly</h2>
</section>
</div>
<div class="slide hidden" id="slide-2">
<section class="slide-content"><h3 id="o-que-s-o-apis-">O que são apis?</h3>
<p>Da <strong>Wikipedia</strong>:</p>
<p>API, de Application Programming Interface (Interface de Programação de Aplicativos) é um conjunto de rotinas e padrões estabelecidos por um software para a utilização das suas funcionalidades por aplicativos que não pretendem envolver-se em detalhes da implementação do software, mas apenas usar seus serviços.</p>
</section>
</div>
<div class="slide hidden" id="slide-3">
<section class="slide-content"><h3 id="o-que-s-o-mesmo-apis-">O que são mesmo apis?</h3>
<p>É uma forma do site disponibilizar dados de maneira estruturada para ser consumida automaticamente por algum outro programa.</p>
<p>Twitter, Facebook, Youtube, etc inauguraram o uso amplo das APIs permitindo que desenvolvedores independentes expandissem o serviço ou criassem novas formas de visualizar e organizar a informação.</p>
</section>
</div>
<div class="slide hidden" id="slide-4">
<section class="slide-content"><h3 id="o-outro-lado-do-espelho">O outro lado do espelho</h3>
<p>O <strong>Portal da Transparência</strong> por exemplo disponibiliza seus dados brutos. Mas <strong>não</strong> disponibiliza api.</p>
<p>Como acessar os pagamentos de diárias de viagens feitos pelo Ministério do Meio Ambiente no último mês?</p>
</section>
</div>
<div class="slide hidden" id="slide-5">
<section class="slide-content"><h3 id="o-outro-lado-do-espelho-2-">O outro lado do espelho (2)</h3>
<ul>
<li>Portal da Transparência -&gt; Download de Dados -&gt; Diárias de Viagens -&gt; 2014 -&gt; Agosto</li>
<li>Unzip 201408_Diarias.zip</li>
<li>Open 201408_Diarias.csv (ISO-8859-1 e separado por Tabs / 42mb)</li>
<li>Filtrar por Ministério do Meio Ambiente</li>
<li>Processar e visualizar os dados</li>
</ul>
</section>
</div>
<div class="slide hidden" id="slide-6">
<section class="slide-content"><h3 id="e-com-uma-api-">E com uma API?</h3>
<p>GET /api/orgaos</p>
<p>{
id: 44000,
name: &#39;MINISTERIO DO MEIO AMBIENTE&#39;
}</p>
<p>GET /api/diarias/100/2014/08</p>
<p>[{
...
&#39;programa&#39; : &#39;Licenciamento e Qualidade Ambiental&#39;,
&#39;cpf&#39; : &#39;<strong><em>.003.07</em>-</strong>&#39;,
&#39;nome&#39; : &#39;CAMILA ARRUDA BOECHAT&#39;,
&#39;data&#39; : &#39;18/08/2014&#39;,
&#39;valor&#39;: &#39;190.15&#39;
...
}]</p>
<p>}</p>
</section>
</div>
<div class="slide hidden" id="slide-7">
<section class="slide-content"><h3 id="bulk-data-vs-api">Bulk Data vs API</h3>
<ul>
<li>Bulk Data<ul>
<li>Ideal para filtrar ou agrupar por critérios não-previstos</li>
<li>Complicado de manter atualizado e em sync</li>
</ul>
</li>
<li>APIs<ul>
<li>Ideal para fazer requisições pontuais remotas</li>
<li>Dados &#39;sempre&#39; atualizados</li>
<li>Se for bem construida, economiza recursos da tua aplicação</li>
</ul>
</li>
</ul>
</section>
</div>
<div class="slide hidden" id="slide-8">
<section class="slide-content"><h3 id="pedindo-dados">Pedindo dados</h3>
<p>Tem todo tipo e formato de API por ai... os dois padrões mais comuns são:</p>
<ul>
<li>REST - usa a /url e &amp;parametros= para construir a requisição</li>
<li>SOAP - usa XML tanto no request quanto na resposta</li>
</ul>
</section>
</div>
<div class="slide hidden" id="slide-9">
<section class="slide-content"><h3 id="recebendo-dados">Recebendo dados</h3>
<p>Tem todo tipo e formato de dados por ai... os padrões mais comuns são:</p>
<ul>
<li>JSON - pode ser lido nativamente com javascript)<ul>
<li>GeoJSON</li>
</ul>
</li>
<li>XML<ul>
<li>RSS, KML, etc </li>
</ul>
</li>
<li>RDF - web &#39;semantica&#39; (nome do campo, valor, definição)</li>
</ul>
<p>Normalmente JSON é um pouco mais simples de trabalhar e as triplas RDF o mais complicado. Mas vai do gosto do freguês.</p>
<h3 id="algumas-apis-doidas">Algumas APIs doidas</h3>
<ul>
<li>SICONV</li>
<li>Câmara Federal</li>
<li>Senado Federal</li>
<li>Google Maps</li>
<li>OpenStreet Maps</li>
</ul>
</section>
</div>
<div class="slide hidden" id="slide-10">
<section class="slide-content"><h3 id="siconv">SICONV</h3>
<p>Sistema de Convênio do Governo Federal
URL: <a href="http://api.convenios.gov.br/siconv/doc/">http://api.convenios.gov.br/siconv/doc/</a></p>
<p>Exemplo: <a href="http://api.convenios.gov.br/siconv/v1/consulta/convenios.json?id_orgao_concedente=44000">http://api.convenios.gov.br/siconv/v1/consulta/convenios.json?id_orgao_concedente=44000</a></p>
</section>
</div>
<div class="slide hidden" id="slide-11">
<section class="slide-content"><h3 id="c-mara-federal">Câmara Federal</h3>
<p>Dados do processo legislativo na Câmara Federal</p>
<p>URL: <a href="http://www2.camara.leg.br/transparencia/dados-abertos/dados-abertos-legislativo">http://www2.camara.leg.br/transparencia/dados-abertos/dados-abertos-legislativo</a></p>
<p>Exemplo: <a href="http://www.camara.gov.br/SitCamaraWS/Proposicoes.asmx/ObterProposicao?tipo=PL&amp;numero=1876&amp;ano=1999">http://www.camara.gov.br/SitCamaraWS/Proposicoes.asmx/ObterProposicao?tipo=PL&amp;numero=1876&amp;ano=1999</a></p>
</section>
</div>
<div class="slide hidden" id="slide-12">
<section class="slide-content"><h3 id="senado-federal">Senado Federal</h3>
<p>Dados do processo legislativo no Senado Federal</p>
<p>URL: <a href="http://legis.senado.gov.br/dadosabertos/docs/">http://legis.senado.gov.br/dadosabertos/docs/</a></p>
<p>Exemplo: <a href="http://legis.senado.gov.br/dadosabertos/materia/completa/plc/30/2011">http://legis.senado.gov.br/dadosabertos/materia/completa/plc/30/2011</a></p>
</section>
</div>
<div class="slide hidden " id="slide-13">
<section class="slide-content"><h3 id="google-maps">Google Maps</h3>
<p>Exibição de mapas, geocodificação de endereços</p>
<p>URL: <a href="https://developers.google.com/maps/?hl=pt-br">https://developers.google.com/maps/?hl=pt-br</a></p>
</section>
</div>
<div class="slide hidden" id="slide-14">
<section class="slide-content"><h3 id="openstreet-maps">OpenStreet Maps</h3>
<p>Exibição de mapas, geocodificação de endereços (livre!)</p>
<p>URL: <a href="http://wiki.openstreetmap.org/wiki/API_v0.6">http://wiki.openstreetmap.org/wiki/API_v0.6</a></p>
</section>
</div>
<div class="slide hidden" id="slide-15">
<section class="slide-content"><div class="author">
<h1 class="name">Pedro Markun</h1>
<h3 class="twitter">
<a href="http://twitter.com/@markun">@markun</a>
</h3>
<h3 class="url">
<a href="http://blog.markun.com.br">http://blog.markun.com.br</a>
</h3>
</div>
</section>
</div>
<div class="controls">
<div class="arrow prev"></div>
<div class="arrow next"></div>
</div>
<script type="text/javascript">
/**
* Returns the current page number of the presentation.
*/
function currentPosition() {
return parseInt(document.querySelector('.slide:not(.hidden)').id.slice(6));
}
/**
* Navigates forward n pages
* If n is negative, we will navigate in reverse
*/
function navigate(n) {
var position = currentPosition();
var numSlides = document.getElementsByClassName('slide').length;
/* Positions are 1-indexed, so we need to add and subtract 1 */
var nextPosition = (position - 1 + n) % numSlides + 1;
/* Normalize nextPosition in-case of a negative modulo result */
nextPosition = (nextPosition - 1 + numSlides) % numSlides + 1;
document.getElementById('slide-' + position).classList.add('hidden');
document.getElementById('slide-' + nextPosition).classList.remove('hidden');
updateProgress();
updateURL();
updateTabIndex();
}
/**
* Updates the current URL to include a hashtag of the current page number.
*/
function updateURL() {
window.history.replaceState({} , null, '#' + currentPosition());
}
/**
* Sets the progress indicator.
*/
function updateProgress() {
var progressBar = document.querySelector('.progress-bar');
if (progressBar !== null) {
var numSlides = document.getElementsByClassName('slide').length;
var position = currentPosition() - 1;
var percent = (numSlides === 1) ? 100 : 100 * position / (numSlides - 1);
progressBar.style.width = percent.toString() + '%';
}
}
/**
* Removes tabindex property from all links on the current slide, sets
* tabindex = -1 for all links on other slides. Prevents slides from appearing
* out of control.
*/
function updateTabIndex() {
var allLinks = document.querySelectorAll('.slide a');
var position = currentPosition();
var currentPageLinks = document.getElementById('slide-' + position).querySelectorAll('a');
var i;
for (i = 0; i < allLinks.length; i++) {
allLinks[i].setAttribute('tabindex', -1);
}
for (i = 0; i < currentPageLinks.length; i++) {
currentPageLinks[i].removeAttribute('tabindex');
}
}
/**
* Determines whether or not we are currently in full screen mode
*/
function isFullScreen() {
return document.fullscreenElement ||
document.mozFullScreenElement ||
document.webkitFullscreenElement ||
document.msFullscreenElement;
}
/**
* Toggle fullScreen mode on document element.
* Works on chrome (>= 15), firefox (>= 9), ie (>= 11), opera(>= 12.1), safari (>= 5).
*/
function toggleFullScreen() {
/* Convenient renames */
var docElem = document.documentElement;
var doc = document;
docElem.requestFullscreen =
docElem.requestFullscreen ||
docElem.msRequestFullscreen ||
docElem.mozRequestFullScreen ||
docElem.webkitRequestFullscreen.bind(docElem, Element.ALLOW_KEYBOARD_INPUT);
doc.exitFullscreen =
doc.exitFullscreen ||
doc.msExitFullscreen ||
doc.mozCancelFullScreen ||
doc.webkitExitFullscreen;
isFullScreen() ? doc.exitFullscreen() : docElem.requestFullscreen();
}
document.addEventListener('DOMContentLoaded', function () {
// Update the tabindex to prevent weird slide transitioning
updateTabIndex();
// If the location hash specifies a page number, go to it.
var page = window.location.hash.slice(1);
if (page) {
navigate(parseInt(page) - 1);
}
document.onkeydown = function (e) {
var kc = e.keyCode;
// left, down, H, J, backspace, PgUp - BACK
// up, right, K, L, space, PgDn - FORWARD
// enter - FULLSCREEN
if (kc === 37 || kc === 40 || kc === 8 || kc === 72 || kc === 74 || kc === 33) {
navigate(-1);
} else if (kc === 38 || kc === 39 || kc === 32 || kc === 75 || kc === 76 || kc === 34) {
navigate(1);
} else if (kc === 13) {
toggleFullScreen();
}
};
if (document.querySelector('.next') && document.querySelector('.prev')) {
document.querySelector('.next').onclick = function (e) {
e.preventDefault();
navigate(1);
};
document.querySelector('.prev').onclick = function (e) {
e.preventDefault();
navigate(-1);
};
}
});
</script>
</body>
</html>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment