HTTP request

HTTP /pictures/kitty.jpg /HTTP/1.1
HTTP /pictures/kitty.jpg /HTTP/2.0

header section below

HTTP /pictures/kitty.jpg /HTTP/2.0
Host: www.google.com
User-Agent: Mizilla/5.0
Connection: keep-alive
Accept: text/html
If-None-Match: fd87e6789

HTTP Response
—-
HTTP/1.1 200 OK
Content-Length: 16824 (※how many byte server send)
Server: Apache
Content-Type: text/html
Date: Wed, 06 Apr 2016
Etag: fd87e6789

binary data

http

fetch("http://www.example.com", {
	"method": "GET ",
	"headers": {

	}
});
fetch("password.txt", {
	"method": "PUT",
	"headers": {
		"exercise": "fetch rocks!"
	}
});

Heroku account

get start Heroku account
Heroku

Heroku CLI
https://devcenter.heroku.com/articles/heroku-cli

To verify your CLI installation use the heroku –version command.

heroku-cli/5.6.12-1708b34 (windows-386) go1.7.4

heroku create

> heroku create
Creating app... done, radiant-dawn-72472
https://radiant-dawn-72472.herokuapp.com/ | https://git.heroku.com/radiant-dawn-72472.git

To ensure you have properly created this remote, run the git remote -v command, you should see something output that reveals the two remotes listed, origin and heroku.

> git remote -v
heroku  https://git.heroku.com/radiant-dawn-72472.git (fetch)
heroku  https://git.heroku.com/radiant-dawn-72472.git (push)
origin  https://github.com/udacity/galeria.git (fetch)
origin  https://github.com/udacity/galeria.git (push)

Once you have your application deployed, Heroku will provide you with a URL you can visit to see your site. After this you can run heroku open. This will open up a browser window and navigate to the deployed application URL.

https://dashboard.heroku.com/apps

If you want to change the URL of your application in the future you can do this by logging into your Heroku Dashboard. Many other actions are also available on the dashboard.

Deployment pipeline
development->staging->production

Heroku will allow you one “dyno” or single command container for free. This means that on a free tier Heroku account, you can run one command on the container and you will not be charged for it.

bundle install

[vagrant@localhost ruby3]$ bundle install
Fetching gem metadata from https://rubygems.org/...........
Fetching version metadata from https://rubygems.org/.
Using json 1.8.3
Installing multi_xml 0.5.5
Installing rack 1.6.4
Installing tilt 2.0.2
Using bundler 1.13.6
Installing httparty 0.13.7
Using rack-protection 1.5.3
Using sinatra 1.4.7
Bundle complete! 3 Gemfile dependencies, 8 gems now installed.
Use `bundle show [gemname]` to see where a bundled gem is installed.
Post-install message from httparty:
When you HTTParty, you must party hard!
get '/product' do
	...
	@products = []
	LOCATIONS.each do |location|
	 @product.push DATA.select { |product| product['location'] == location }.sample
end
<% @product.each do |product| %>
<a href='/products/location<%= product&#91;location&#93; %>'>
<div class='product'>
	<div class='thumb'>
		<img src='<%= product&#91;'url'&#93; %>'>
	</div>
	<div class='caption'>
		<%= product&#91;'location'&#93; != 'us' ? product&#91;'location'&#93;.capitalize : product&#91;'location'&#93;.upcase %>
		</div>
	</div>
</a>
<% end %>
get '/products/location/:location' do
	DATA = HTTParty.get('https://fomotograph-api.udacity.com/products.json')['photos']
	@products = DATA.select{ |product| product['location'] == params[:location]}
	erb "<!DOCTYPE html>..."
end


get '/products/:id' do
	DATA = HTTPartyp.get('https://hogehoge/products.json')['photos']
	@product = DATA.select{ |prod| prod['id'] == params[:id].to_i }.first
	erb "<!DOCTYPE html> ..."
end	
class Product

	url = 'https://fomotograph-api.com/product.json'
	DATA = HTTParty.get(url)['photos']
end
require 'HTTParty'
require 'json'

class Product

	url = 'https://fomotograph-api.com/product.json'
	DATA = HTTParty.get(url)['photos']

	def initialize(product_data = {})
	@id = product_data['id']
	@title = product_data['title']
	@location = product_data['location']
	@summary = product_data['summary']
	@url = product_data['url']
	@price = product_data['price']
	end

	def self.all
		DATA.map { |product| new(product) }
	end

	def self.sample_locations
		@products = []
		LOCATIONS.each do |location|
		@products.push self.all.select { |product| product.location == location }.sample_locations
		end
		return @product
	end

	def self.find_by_location(location)
		self.all.select { |product| product.location == location }
	end
end
{
	"id"=>27, "title"=>"worlds end", "summary"=>"travel tothe end ...",
	"location"=>"scotland", "price"=>37, "url"=>"/images/scotland/worlds-end.jpg"
}

controller

get '/products' do
	@products = Product.all
	erb :products
end

template engine ERB

There are tons of different templating languages out there that we could use to create dynamic webpages, but the one we’re going to work with is called ERB. ERB, Embedded Ruby, is the most commonly used templating language with Ruby web frameworks like Sinatra or Ruby on Rails.

The key concept of ERB is simple: it allows you to write HTML with bits of Ruby code interspersed with regular HTML. Before the template is sent back to the user, it’s compiled. This means that any Ruby code in the template is executed, and all we’re left with is regular HTML.

Brackets are used to wrap the embedded Ruby code, to distinguish it from the HTML.
<% %>

We can also use ERB to insert dynamic data into templates. To do that we need to use a slightly different syntax:
<%= %>

views/home.erb

<% 5.times do %>
  <h1>Today's date is <%= Time.now %></h1>
<% end %>

app.ruby

require "sinatra"

get "/" do
   erb :home
end
vagrant@localhost ruby2]$ ruby app.rb -o 192.168.33.10
== Sinatra (v1.4.7) has taken the stage on 4567 for development with backup from Puma
Puma starting in single mode...
* Version 3.6.0 (ruby 2.3.1-p112), codename: Sleepy Sunday Serenity
* Min threads: 0, max threads: 16
* Environment: development
* Listening on tcp://192.168.33.10:4567
Use Ctrl-C to stop

e

extreamly easy way!

rendering HTML

require "sinatra"

get "/" do
  "<h1>Welcome to the <em>homepage</em></h1>"
end

get "/sinatra" do
  "<h3>I love <a href='http://www.sinatrarb.com/'>Sinatra!</a></h3>"
end

get "/square/:num" do
  num = params[:num].to_i
  num * num
end

b

require "sinatra"

get "/cat" do
   send_file "cat.html"
end

start running Sinatra

require "sinatra"
get "/" do
  puts "you requested the root path"
end

Here we go!

require "sinatra"
get "/" do
  "you requested the root path"
end

get "/about" do
  "this app is our first Sinatra App!"
end

get "/roll-die" do
  "Your die roll is...#{rand(1...7)}"
end

a

use variable in routing

require "sinatra"
get "/r/SUBREDDIT_NAME/POST_ID/POST_TITLE" do
  "this is a post"
end

getting a patter with post

require "sinatra"

get "/greet/:name" do
  "Hello there #{params[:name]}!"
end

Think about capitalize

get "/greet/:name" do
  name = params[:name].capitalize
  "Hello there #{name}!"
end

try out this

get "/square/:num" do
  num = params[:num].to_i
  num * num
end

typical sinatra

get '/about' do
	send_file 'about.html'
end

Gemfile

source 'https://rubygems.org'

gem 'sinatra'

gem install sinatra
gem install sinatra-contrib

[vagrant@localhost webapp]$ gem install sinatra
Successfully installed sinatra-1.4.7
Parsing documentation for sinatra-1.4.7
Done installing documentation for sinatra after 0 seconds
1 gem installed

let’s try this

[vagrant@localhost ruby2]$ ruby app.ruby -o 192.168.33.10
ruby: No such file or directory -- app.ruby (LoadError)
[vagrant@localhost ruby2]$ ruby app.rb -o 192.168.33.10
== Sinatra (v1.4.7) has taken the stage on 4567 for development with backup from Puma
Puma starting in single mode...
* Version 3.6.0 (ruby 2.3.1-p112), codename: Sleepy Sunday Serenity
* Min threads: 0, max threads: 16
* Environment: development
* Listening on tcp://192.168.33.10:4567
Use Ctrl-C to stop
192.168.33.1 - - [14/Jan/2017:08:54:48 +0900] "GET / HTTP/1.1" 404 466 0.0379
192.168.33.1 - - [14/Jan/2017:08:54:48 +0900] "GET /__sinatra__/404.png HTTP/1.1" 200 18893 0.0065
192.168.33.1 - - [14/Jan/2017:08:54:48 +0900] "GET /favicon.ico HTTP/1.1" 404 477 0.0007
^C== Sinatra has ended his set (crowd applauds)
- Gracefully stopping, waiting for requests to finish
=== puma shutdown: 2017-01-14 08:55:18 +0900 ===
- Goodbye!

無題

verb path do
  #do something!
end

here is a example

post '/login' do
  #do something!
end

EventListening

function setup() {
	document.getElementById('canvas').addEventListener('mousemove',onMouseMove);
	document.getElementById('canvas').addEventListener('keydown',onKeyDown);
}
function onMouseMove(event) {
	var posx = event.clientX;
	var posy = event.clientY;
	console.log("(", posx, ", ", posy, ")");
}
function onKeyDown(event) {
	var keyID = event.keyID;
	console.log("ID: ", keyID);
}

json

{
	"frames": {

		"chaingun.png": {
			"frame": {
				"x": 1766,
				"y": 202,
				"w": 42,
				"h": 34
			},
			"rotated": false,
			"trimmed": true,
			"spriteSourceSize": {
				"x": 38,
				"y": 32,
				"w": 42,
				"h": 34
			},
			"sourceSize": {
				"w": 128,
				"h": 128
			}
		},
		"chaingun_impact.png": {
			"frame": {
				"x": 1162,
				"y": 322,
				"w": 38,
				"h": 34
			},
			"rotated": false,
			"trimmed": true,
			"spriteSourceSize": {
				"x": 110,
				"y": 111,
				"w": 38,
				"h": 34
			},
			"sourceSize": {
				"w": 256,
				"h": 256
			}
		},
		"chaingun_impact_0000.png": {
			"frame": {
				"x": 494,
				"y": 260,
				"w": 22,
				"h": 22
			},
			"rotated": false,
			"trimmed": true,
			"spriteSourceSize": {
				"x": 113,
				"y": 108,
				"w": 22,
				"h": 22
			},
			"sourceSize": {
				"w": 256,
				"h": 256
			}
		},
		"chaingun_impact_0001.png": {
			"frame": {
				"x": 1500,
				"y": 1904,
				"w": 34,
				"h": 30
			},
			"rotated": false,
			"trimmed": true,
			"spriteSourceSize": {
				"x": 104,
				"y": 104,
				"w": 34,
				"h": 30
			},
			"sourceSize": {
				"w": 256,
				"h": 256
			}
		},
		"chaingun_impact_0002.png": {
			"frame": {
				"x": 888,
				"y": 366,
				"w": 38,
				"h": 32
			},
			"rotated": false,
			"trimmed": true,
			"spriteSourceSize": {
				"x": 106,
				"y": 105,
				"w": 38,
				"h": 32
			},
			"sourceSize": {
				"w": 256,
				"h": 256
			}
		},
		"chaingun_impact_0003.png": {
			"frame": {
				"x": 990,
				"y": 84,
				"w": 32,
				"h": 28
			},
			"rotated": false,
			"trimmed": true,
			"spriteSourceSize": {
				"x": 113,
				"y": 109,
				"w": 32,
				"h": 28
			},
			"sourceSize": {
				"w": 256,
				"h": 256
			}
		}
	},
	"meta": {
		"app": "http://www.texturepacker.com",
		"version": "1.0",
		"image": "assets/grits_effects.png",
		"format": "RGBA8888",
		"size": {
			"w": 2048,
			"h": 2048
		},
		"scale": "1",
		"smartupdate": "$TexturePacker:SmartUpdate:a5e0b1932a348d048c58a625408c4276$"
	}
}
parseAtlasDefinition: function (atlasJSON){
	var parsed = JSON.parse(atlasJSON);

	for(var key in parsed.frames){
	var sprite = parsed.frames[key];

	var cx = -sprite.frame.w * 0.5;
	var cy = -sprite.frame.h * 0.5;

	// Define the sprite for this sheet.
	this.defSprite(key, sprite.frame.x, sprite.frame.y, sprite.frame.z)
	}
}
});

function drawSprite(spritename, posX, posY){
	
}

function __drawSpriteInternal(spt, sheet, posX, posY){
	
}

var gSpriteSheets = {};

SpriteSheetClass = Class.exnted({
	
});

function drawSprite(spritename, posX, posY){
	for(var sheetName in gSpriteSheets){
		var sheet = gSpriteSheetsd[sheetName];
		var sprite = sheet.getStats(spritename);
		if(sprite == null) continue;

		__drawSpriteInternal(sprite, sheet, posX, posY);

		return;
	}
}

set interval

var canvas = null;
var ctx = null;
var frameRate = 1000/30;
var frame = 0;
var assets = ['/media/img/gamedev/robowalk/robowalk00.png',
              '/media/img/gamedev/robowalk/robowalk01.png',
              '/media/img/gamedev/robowalk/robowalk02.png',
              '/media/img/gamedev/robowalk/robowalk03.png',
              '/media/img/gamedev/robowalk/robowalk04.png',
              '/media/img/gamedev/robowalk/robowalk05.png',
              '/media/img/gamedev/robowalk/robowalk06.png',
              '/media/img/gamedev/robowalk/robowalk07.png',
              '/media/img/gamedev/robowalk/robowalk08.png',
              '/media/img/gamedev/robowalk/robowalk09.png',
              '/media/img/gamedev/robowalk/robowalk10.png',
              '/media/img/gamedev/robowalk/robowalk11.png',
              '/media/img/gamedev/robowalk/robowalk12.png',
              '/media/img/gamedev/robowalk/robowalk13.png',
              '/media/img/gamedev/robowalk/robowalk14.png',
              '/media/img/gamedev/robowalk/robowalk15.png',
              '/media/img/gamedev/robowalk/robowalk16.png',
              '/media/img/gamedev/robowalk/robowalk17.png',
              '/media/img/gamedev/robowalk/robowalk18.png'
             ];
var frames = [];

var onImageLoad = function(){
    console.log("IMAGE!!!");
};

var setup = function() {
    body = document.getElementById('body');
    canvas = document.createElement('canvas');

    ctx = canvas.getContext('2d');
    
    canvas.width = 100;
    canvas.height = 100;

    body.appendChild(canvas);

    for(var i = 0; i < assetes.length; i++){
    	frames.push(new Image());
    	frames[i].src = asset[i];
    	frames[i].onload = onImageLoad;
    }
    setInterval(animate, frameRate);
};

var animate = function(){
    context.clearRect(0,0,canvas.width, canvas.height);
    frame = (frame + 1) % frames.length;
};

setup();