integrated responder framework
This commit is contained in:
		
							
								
								
									
										4
									
								
								.gitignore
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										4
									
								
								.gitignore
									
									
									
									
										vendored
									
									
										Normal file
									
								
							| @@ -0,0 +1,4 @@ | ||||
| __pycache__/ | ||||
| venv/ | ||||
| .idea/ | ||||
|  | ||||
							
								
								
									
										11
									
								
								app_instance.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										11
									
								
								app_instance.py
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,11 @@ | ||||
| import responder | ||||
|  | ||||
| # CORS wasn't demoed in the course, but is required to be used from | ||||
| # external apps like movie exploder. | ||||
|  | ||||
| cors_params = { | ||||
|     'allow_origins': '*', | ||||
|     'allow_methods': '*', | ||||
| } | ||||
|  | ||||
| api = responder.API(cors=True, cors_params=cors_params) | ||||
							
								
								
									
										33
									
								
								css/docs.css
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										33
									
								
								css/docs.css
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,33 @@ | ||||
| .request { | ||||
|     font-family: Menlo, Monaco, Consolas, "Courier New", monospace; | ||||
|     font-weight: bold; | ||||
|     border: 1px solid gray; | ||||
|     border-radius: 5px; | ||||
|     padding: 10px; | ||||
|     font-size: 24px; | ||||
| } | ||||
|  | ||||
| .get { | ||||
|     color: #2b542c; | ||||
|     background-color: #beffbd; | ||||
| } | ||||
|  | ||||
| .post { | ||||
|     color: #ae5900; | ||||
|     background-color: #ffc79d; | ||||
| } | ||||
|  | ||||
| .response_formats span { | ||||
|     font-weight: bold; | ||||
|     color: darkred; | ||||
|     font-family: Menlo, Monaco, Consolas, "Courier New", monospace; | ||||
| } | ||||
|  | ||||
| pre { | ||||
|     font-family: Menlo, Monaco, Consolas, "Courier New", monospace; | ||||
| } | ||||
|  | ||||
| ul li { | ||||
|     font-size: 18px; | ||||
|     margin-bottom: 10px; | ||||
| } | ||||
							
								
								
									
										184
									
								
								css/theme.css
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										184
									
								
								css/theme.css
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,184 @@ | ||||
| @import url(//fonts.googleapis.com/css?family=Open+Sans:300,400,600,700); | ||||
|  | ||||
| body { | ||||
|     font-family: "Open Sans", "Helvetica Neue", Helvetica, Arial, sans-serif; | ||||
|     font-weight: 300; | ||||
|     color: black; | ||||
|     background: white; | ||||
| } | ||||
|  | ||||
| h1, | ||||
| h2, | ||||
| h3, | ||||
| h4, | ||||
| h5, | ||||
| h6 { | ||||
|     font-family: "Open Sans", "Helvetica Neue", Helvetica, Arial, sans-serif; | ||||
|     font-weight: 300; | ||||
| } | ||||
|  | ||||
| p { | ||||
|     font-weight: 300; | ||||
| } | ||||
|  | ||||
| .font-normal { | ||||
|     font-weight: 400; | ||||
| } | ||||
|  | ||||
| .font-semi-bold { | ||||
|     font-weight: 600; | ||||
| } | ||||
|  | ||||
| .font-bold { | ||||
|     font-weight: 700; | ||||
| } | ||||
|  | ||||
| .starter-template { | ||||
|     margin-top: 25px; | ||||
| } | ||||
|  | ||||
| .starter-template .content { | ||||
|     margin-left: 10px; | ||||
| } | ||||
|  | ||||
| .starter-template .content h1 { | ||||
|     margin-top: 10px; | ||||
|     font-size: 60px; | ||||
| } | ||||
|  | ||||
| .starter-template .content h1 .smaller { | ||||
|     font-size: 40px; | ||||
| } | ||||
|  | ||||
| .starter-template .content .lead { | ||||
|     font-size: 25px; | ||||
| } | ||||
|  | ||||
| .starter-template .links { | ||||
|     float: right; | ||||
|     right: 0; | ||||
|     margin-top: 125px; | ||||
| } | ||||
|  | ||||
| .starter-template .links ul { | ||||
|     display: block; | ||||
|     padding: 0; | ||||
|     margin: 0; | ||||
| } | ||||
|  | ||||
| .starter-template .links ul li { | ||||
|     list-style: none; | ||||
|     display: inline; | ||||
|     margin: 0 10px; | ||||
| } | ||||
|  | ||||
| .starter-template .links ul li:first-child { | ||||
|     margin-left: 0; | ||||
| } | ||||
|  | ||||
| .starter-template .links ul li:last-child { | ||||
|     margin-right: 0; | ||||
| } | ||||
|  | ||||
| .starter-template .links ul li.current-version { | ||||
|     font-weight: 400; | ||||
| } | ||||
|  | ||||
| .starter-template .links ul li a, a { | ||||
|     text-decoration: underline; | ||||
| } | ||||
|  | ||||
| .starter-template .links ul li a:hover, a:hover { | ||||
|     text-decoration: underline; | ||||
| } | ||||
|  | ||||
| .starter-template .links ul li .icon-muted { | ||||
|     margin-right: 5px; | ||||
| } | ||||
|  | ||||
| .starter-template .copyright { | ||||
|     margin-top: 10px; | ||||
|     font-size: 0.9em; | ||||
|     text-transform: lowercase; | ||||
|     float: right; | ||||
|     right: 0; | ||||
| } | ||||
|  | ||||
| @media (max-width: 1199px) { | ||||
|     .starter-template .content h1 { | ||||
|         font-size: 45px; | ||||
|     } | ||||
|  | ||||
|     .starter-template .content h1 .smaller { | ||||
|         font-size: 30px; | ||||
|     } | ||||
|  | ||||
|     .starter-template .content .lead { | ||||
|         font-size: 20px; | ||||
|     } | ||||
| } | ||||
|  | ||||
| @media (max-width: 991px) { | ||||
|     .starter-template { | ||||
|         margin-top: 0; | ||||
|     } | ||||
|  | ||||
|     .starter-template .logo { | ||||
|         margin: 40px auto; | ||||
|     } | ||||
|  | ||||
|     .starter-template .content { | ||||
|         margin-left: 0; | ||||
|         text-align: center; | ||||
|     } | ||||
|  | ||||
|     .starter-template .content h1 { | ||||
|         margin-bottom: 20px; | ||||
|     } | ||||
|  | ||||
|     .starter-template .links { | ||||
|         float: none; | ||||
|         text-align: center; | ||||
|         margin-top: 60px; | ||||
|     } | ||||
|  | ||||
|     .starter-template .copyright { | ||||
|         float: none; | ||||
|         text-align: center; | ||||
|     } | ||||
| } | ||||
|  | ||||
| @media (max-width: 767px) { | ||||
|     .starter-template .content h1 .smaller { | ||||
|         font-size: 25px; | ||||
|         display: block; | ||||
|     } | ||||
|  | ||||
|     .starter-template .content .lead { | ||||
|         font-size: 16px; | ||||
|     } | ||||
|  | ||||
|     .starter-template .links { | ||||
|         margin-top: 40px; | ||||
|     } | ||||
|  | ||||
|     .starter-template .links ul li { | ||||
|         display: block; | ||||
|         margin: 0; | ||||
|     } | ||||
|  | ||||
|     .starter-template .links ul li .icon-muted { | ||||
|         display: none; | ||||
|     } | ||||
|  | ||||
|     .starter-template .copyright { | ||||
|         margin-top: 20px; | ||||
|     } | ||||
| } | ||||
|  | ||||
|  | ||||
| .disclaimer { | ||||
|     margin-top: 20px; | ||||
|     font-style: italic; | ||||
|  | ||||
| } | ||||
							
								
								
									
										12
									
								
								routes.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										12
									
								
								routes.py
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,12 @@ | ||||
| # noinspection PyUnresolvedReferences | ||||
| from app_instance import api | ||||
| # noinspection PyUnresolvedReferences | ||||
| from views.api_views import * | ||||
| # noinspection PyUnresolvedReferences | ||||
| from views.home import * | ||||
| # noinspection PyUnresolvedReferences | ||||
| from views.temp_css import * | ||||
| # noinspection PyUnresolvedReferences | ||||
| from views.player import * | ||||
|  | ||||
| api.add_route("/static", static=True) | ||||
							
								
								
									
										120
									
								
								server.py
									
									
									
									
									
										
										
										Normal file → Executable file
									
								
							
							
						
						
									
										120
									
								
								server.py
									
									
									
									
									
										
										
										Normal file → Executable file
									
								
							| @@ -1,90 +1,48 @@ | ||||
| import time | ||||
| #!/usr/bin/env python3 | ||||
|  | ||||
| import random | ||||
|  | ||||
|  | ||||
| # Karten: 1-13 in Blau, Rot, Gelb, Gruen und 4xZ und 4xN | ||||
|  | ||||
|  | ||||
| def chunks(lst, n): | ||||
|     """Yield successive n-sized chunks from lst.""" | ||||
|     for i in range(0, len(lst), n): | ||||
|         yield lst[i:i + n] | ||||
|  | ||||
|  | ||||
| class Card: | ||||
|     def __init__(self, color, value): | ||||
|         self.color = color | ||||
|         self.value = value | ||||
|  | ||||
|     def __str__(self): | ||||
|         sc = self.color if self.color else ' ' | ||||
|         sv = str(self.value) | ||||
|         return sc+' '+sv | ||||
|  | ||||
|     def __repr__(self): | ||||
|         return str(self) | ||||
|  | ||||
| class Player: | ||||
|     def __init__(self, name, player_id): | ||||
|         self.name = name | ||||
|         self.id = player_id | ||||
|         self.cards = [] | ||||
|  | ||||
|     def deal_cards(self, cards): | ||||
|         self.cards = cards | ||||
|  | ||||
|     def show_cards(self): | ||||
|         print(self.cards) | ||||
|  | ||||
|  | ||||
| class WizGame: | ||||
|     def __init__(self): | ||||
|         self.players = [] | ||||
|         self.card_deck = [] | ||||
|  | ||||
|     def create_deck(self): | ||||
|         for color in ["blue", "red", "green", "yellow"]: | ||||
|             for val in range(1,14): | ||||
|                 self.card_deck.append(Card(color, val)) | ||||
|         for _ in range(1,5): | ||||
|             self.card_deck.append(Card(None, 'Z')) | ||||
|         for _ in range(1,5): | ||||
|             self.card_deck.append(Card(None, 'N')) | ||||
|         print("carddeck:") | ||||
|         print(self.card_deck) | ||||
|  | ||||
|     def deal_cards(self): | ||||
|         random.shuffle(self.card_deck) | ||||
|         num_cards = int(len(self.card_deck)/len(self.players)) | ||||
|         print(num_cards) | ||||
|         cs = list(chunks(self.card_deck, num_cards)) | ||||
|         for i in range(len(self.players)): | ||||
|             self.players[i].deal_cards(cs[i]) | ||||
|             self.players[i].show_cards() | ||||
|  | ||||
|     def add_player(self, name: str, player_id): | ||||
|         if len(self.players) < 6: | ||||
|             self.players.append((Player(name, player_id))) | ||||
|  | ||||
|  | ||||
| import socket | ||||
| import responder | ||||
| from app_instance import api | ||||
| from routes import * | ||||
| import wiz_game | ||||
|  | ||||
| def main(): | ||||
|     print("main started") | ||||
|     w = WizGame() | ||||
|     w.create_deck() | ||||
|     w.add_player("p1", 1) | ||||
|     w.add_player("p2", 2) | ||||
|     w.add_player("p3", 3) | ||||
|     w.add_player("p4", 4) | ||||
|     w.deal_cards() | ||||
|     print("round 2") | ||||
|     w.deal_cards() | ||||
|     print("round 3") | ||||
|     w.deal_cards() | ||||
|     print("round 4") | ||||
|     w.deal_cards() | ||||
|  | ||||
|     random.seed() | ||||
|  | ||||
|     wiz_game.the_game.create_deck() | ||||
|     wiz_game.the_game.add_player("p1", 1) | ||||
|     wiz_game.the_game.add_player("p2", 2) | ||||
|     wiz_game.the_game.add_player("p3", 3) | ||||
|     wiz_game.the_game.add_player("p4", 4) | ||||
|     wiz_game.the_game.deal_cards(4) | ||||
|  | ||||
|     api.run(port=19203, address="127.0.0.1") | ||||
|     exit(0) | ||||
|  | ||||
| #    w.create_deck() | ||||
| #    w.add_player("p1", 1) | ||||
| #    w.add_player("p2", 2) | ||||
| #    w.add_player("p3", 3) | ||||
| #    w.add_player("p4", 4) | ||||
| #    w.deal_cards(1) | ||||
| #    print("round 2") | ||||
| #    w.deal_cards(2) | ||||
| #    print("round 3") | ||||
| #    w.deal_cards(3) | ||||
| #    print("round 4") | ||||
| #    w.deal_cards(4) | ||||
| #    print("round 12") | ||||
| #    w.deal_cards(12) | ||||
| #    print("round 13") | ||||
| #    w.deal_cards(13) | ||||
| #    print("round 14") | ||||
| #    w.deal_cards(14) | ||||
| #    print("round 15") | ||||
| #    w.deal_cards(15) | ||||
|  | ||||
|  | ||||
| if __name__ == '__main__': | ||||
|     main() | ||||
|   | ||||
							
								
								
									
										51
									
								
								templates/home/index.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										51
									
								
								templates/home/index.html
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,51 @@ | ||||
| {% extends "/shared/_layout.html" %} | ||||
|  | ||||
| {% block content %} | ||||
|  | ||||
|         <div class="content"> | ||||
|             <h1><span class="font-semi-bold">Gambling Foo</span> <span class="smaller">A RESTful gaming service</span></h1> | ||||
|             <p class="lead"> | ||||
|                 Play a nice game of cards?<br> | ||||
|                 <br> | ||||
|                 <strong>Endpoints</strong> | ||||
|             <ul> | ||||
|                 <li> | ||||
|                     <strong>Shuffle Card Deck</strong><br> | ||||
|                     <a href="/api/shuffle">GET /api/shuffle</a> | ||||
|                 </li> | ||||
|                 <li> | ||||
|                     <strong>Movies by director</strong><br> | ||||
|                     <a href="/api/director/cameron">GET /api/director/{director_name}</a> | ||||
|                 </li> | ||||
| <!-- | ||||
|                 <li> | ||||
|                     <strong>Movie by IMDB code</strong><br> | ||||
|                     <a href="/api/movie/tt0096754">GET /api/movie/{imdb_number}</a> | ||||
|                 </li> | ||||
|                 <li> | ||||
|                     <strong>Top 10 Movies (by IMDB score)</strong><br> | ||||
|                     <a href="/api/movie/top">GET /api/movie/top</a> | ||||
|                 </li> | ||||
|                 <li> | ||||
|                     <strong>All genres</strong><br> | ||||
|                     <a href="/api/movie/genre/all">GET /api/movie/genre/all</a> | ||||
|                 </li> | ||||
|                 <li> | ||||
|                     <strong>Top movies for a given genres</strong><br> | ||||
|                     <a href="/api/movie/genre/sci-fi">GET /api/movie/genre/{genre}</a> | ||||
|                 </li> | ||||
| --> | ||||
|             </ul> | ||||
|             </p> | ||||
|  | ||||
|             <p class="disclaimer"> | ||||
|                 Spam Bacon Sausage + Spam | ||||
|                 Spam Spam Spam Spam Spam | ||||
|                   Spam Baked Beans Spam | ||||
|                   Spam Spam + Spam | ||||
|  | ||||
|             </p> | ||||
|         </div> | ||||
|  | ||||
|  | ||||
| {% endblock %} | ||||
							
								
								
									
										50
									
								
								templates/home/player.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										50
									
								
								templates/home/player.html
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,50 @@ | ||||
| {% extends "/shared/_layout.html" %} | ||||
|  | ||||
| {% block content %} | ||||
|  | ||||
|         <div class="content"> | ||||
|             <h1><span class="font-semi-bold">Gambling Foo</span> <span class="smaller">A RESTful gaming service</span></h1> | ||||
|             <p class="lead"> | ||||
|                 Play a nice game of cards?<br> | ||||
|                 <br> | ||||
|                 <strong>Player {{player}} view</strong> | ||||
|             <table style="width:100%"> | ||||
|                 <tr> | ||||
|                 {% for card in cards %} | ||||
|                     <li> | ||||
|                         <strong>>card {{loop.index}} is: {{card}} </strong><br> | ||||
|                     </li> | ||||
|                 {% endfor %} | ||||
|                      | ||||
| <!-- | ||||
|                 <li> | ||||
|                     <strong>Movie by IMDB code</strong><br> | ||||
|                     <a href="/api/movie/tt0096754">GET /api/movie/{imdb_number}</a> | ||||
|                 </li> | ||||
|                 <li> | ||||
|                     <strong>Top 10 Movies (by IMDB score)</strong><br> | ||||
|                     <a href="/api/movie/top">GET /api/movie/top</a> | ||||
|                 </li> | ||||
|                 <li> | ||||
|                     <strong>All genres</strong><br> | ||||
|                     <a href="/api/movie/genre/all">GET /api/movie/genre/all</a> | ||||
|                 </li> | ||||
|                 <li> | ||||
|                     <strong>Top movies for a given genres</strong><br> | ||||
|                     <a href="/api/movie/genre/sci-fi">GET /api/movie/genre/{genre}</a> | ||||
|                 </li> | ||||
| --> | ||||
|             </table> | ||||
|             </p> | ||||
|  | ||||
|             <p class="disclaimer"> | ||||
|                 Spam Bacon Sausage + Spam | ||||
|                 Spam Spam Spam Spam Spam | ||||
|                   Spam Baked Beans Spam | ||||
|                   Spam Spam + Spam | ||||
|  | ||||
|             </p> | ||||
|         </div> | ||||
|  | ||||
|  | ||||
| {% endblock %} | ||||
							
								
								
									
										64
									
								
								templates/shared/_layout.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										64
									
								
								templates/shared/_layout.html
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,64 @@ | ||||
| <!DOCTYPE html> | ||||
| <html > | ||||
| <head> | ||||
|     <meta charset="utf-8"> | ||||
|     <meta http-equiv="X-UA-Compatible" content="IE=edge"> | ||||
|     <meta name="viewport" content="width=device-width, initial-scale=1.0"> | ||||
|     <meta name="description" content="pyramid web application"> | ||||
|     <meta name="author" content="Pylons Project"> | ||||
|  | ||||
|     <title>MovieDB Service</title> | ||||
|  | ||||
|     <!-- Bootstrap core CSS --> | ||||
|     <link href="//oss.maxcdn.com/libs/twitter-bootstrap/3.0.3/css/bootstrap.min.css" rel="stylesheet"> | ||||
|  | ||||
|     <!-- Custom styles for this scaffold --> | ||||
|     <link href="/css/theme.css" rel="stylesheet"> | ||||
|     <link href="/css/docs.css" rel="stylesheet"> | ||||
|  | ||||
|     <!-- HTML5 shim and Respond.js IE8 support of HTML5 elements and media queries --> | ||||
|     <!--[if lt IE 9]> | ||||
|     <script src="//oss.maxcdn.com/libs/html5shiv/3.7.0/html5shiv.js"></script> | ||||
|     <script src="//oss.maxcdn.com/libs/respond.js/1.3.0/respond.min.js"></script> | ||||
|     <![endif]--> | ||||
| </head> | ||||
|  | ||||
| <body> | ||||
|  | ||||
| <div class="starter-template"> | ||||
|     <div class="container"> | ||||
|         <div class="row"> | ||||
|             <div class="col-md-2"> | ||||
|             </div> | ||||
|             <div class="col-md-10"> | ||||
|                 <div>{% block content %}{% endblock %}</div> | ||||
|             </div> | ||||
|         </div> | ||||
|         <div class="row"> | ||||
|             <div class="links"> | ||||
|                 <ul> | ||||
|                     <li><i class="glyphicon glyphicon-cog icon-muted"></i><a | ||||
|                             href="https://github.com/mikeckennedy/python-jumpstart-course-demos" | ||||
|                             target="_blank">Github Project</a></li> | ||||
|                     <li><i class="glyphicon glyphicon-globe icon-muted"></i><a href="https://twitter.com/talkpython" | ||||
|                                                                                target="_blank">Twitter</a> | ||||
|                     </li> | ||||
|                 </ul> | ||||
|             </div> | ||||
|         </div> | ||||
|         <div class="row"> | ||||
|             <div class="copyright"> | ||||
|                 Copyright © Talk Python Training | ||||
|             </div> | ||||
|         </div> | ||||
|     </div> | ||||
| </div> | ||||
|  | ||||
|  | ||||
| <!-- Bootstrap core JavaScript | ||||
| ================================================== --> | ||||
| <!-- Placed at the end of the document so the pages load faster --> | ||||
| <script src="//oss.maxcdn.com/libs/jquery/1.10.2/jquery.min.js"></script> | ||||
| <script src="//oss.maxcdn.com/libs/twitter-bootstrap/3.0.3/js/bootstrap.min.js"></script> | ||||
| </body> | ||||
| </html> | ||||
							
								
								
									
										39
									
								
								views/api_views.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										39
									
								
								views/api_views.py
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,39 @@ | ||||
| from responder import Response | ||||
|  | ||||
| from app_instance import api | ||||
|  | ||||
| response_count_max = 10 | ||||
|  | ||||
|  | ||||
| @api.route("/api/search/{keyword}") | ||||
| def search_keyword(req, resp, keyword: str): | ||||
|     resp.media = {'keyword': keyword, 'hits': "movie_dicts", 'truncated_results': "limited"} | ||||
|  | ||||
|  | ||||
| @api.route("/api/director/{director_name}") | ||||
| def search_director(_, resp, director_name: str): | ||||
|     resp.media = {'keyword': director_name, 'hits': "movies_dicts", 'truncated_results': "limited"} | ||||
|  | ||||
|  | ||||
| @api.route("/api/movie/genre/{genre}") | ||||
| def movies_by_genre(_, resp: Response, genre: str): | ||||
|     resp.media = {'genre': genre, 'hits': "hits_dicts", 'truncated_results': "limited"} | ||||
|  | ||||
|  | ||||
| @api.route("/api/movie/{imdb_number}") | ||||
| def search_imdb(_, resp, imdb_number: str): | ||||
|     resp.media = {'foo': "bar"} | ||||
|  | ||||
|  | ||||
| @api.route("/api/movie/top") | ||||
| def top_movies(_, resp: Response): | ||||
|     resp.media = {'keyword': "keyword", 'hits': "hits_dicts", 'truncated_results': "limited"} | ||||
|  | ||||
|  | ||||
| @api.route("/api/movie/genre/all") | ||||
| def all_genres(_, resp: Response): | ||||
|     resp.media = {"all": "stuff"} | ||||
|  | ||||
| @api.route("/api/shuffle") | ||||
| def cards_shuffle(_, resp: Response): | ||||
|     resp.media = {"shuffled": "done"} | ||||
							
								
								
									
										6
									
								
								views/home.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										6
									
								
								views/home.py
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,6 @@ | ||||
| from app_instance import api | ||||
|  | ||||
|  | ||||
| @api.route("/") | ||||
| def index(req, resp): | ||||
|     resp.content = api.template('home/index.html') | ||||
							
								
								
									
										11
									
								
								views/player.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										11
									
								
								views/player.py
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,11 @@ | ||||
| from app_instance import api | ||||
|  | ||||
| from wiz_game import the_game | ||||
|  | ||||
|  | ||||
| @api.route("/player/{player}") | ||||
| def index(req, resp, player: str): | ||||
|     p = int(player) | ||||
|     print(p) | ||||
|     print(the_game.players) | ||||
|     resp.content = api.template('home/player.html', player=player, cards=the_game.players[p].cards) | ||||
							
								
								
									
										22
									
								
								views/temp_css.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										22
									
								
								views/temp_css.py
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,22 @@ | ||||
| import os | ||||
|  | ||||
| from app_instance import api | ||||
|  | ||||
|  | ||||
| # This sucks. But at the moment I'm publishing this code / video | ||||
| # Responder has developed a bug where it cannot serve static files | ||||
| # See https://github.com/kennethreitz/responder/issues/337 | ||||
| # | ||||
| # This is just a work around so you all can enjoy the course. | ||||
|  | ||||
| @api.route("/css/{file}") | ||||
| def css(req, resp, file): | ||||
|     resp.headers['Content-Type'] = 'text/css' | ||||
|     full_file = os.path.join( | ||||
|         os.path.dirname(__file__), | ||||
|         '..', | ||||
|         'css', | ||||
|         file | ||||
|     ) | ||||
|     with open(full_file, encoding='utf-8') as fin: | ||||
|         resp.content = fin.read() | ||||
							
								
								
									
										83
									
								
								wiz_game.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										83
									
								
								wiz_game.py
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,83 @@ | ||||
|  | ||||
| import random | ||||
|  | ||||
| def chunks(lst, n): | ||||
|     """Yield successive n-sized chunks from lst.""" | ||||
|     for i in range(0, len(lst), n): | ||||
|         yield lst[i:i + n] | ||||
|  | ||||
|  | ||||
| class Card: | ||||
|     def __init__(self, color, value): | ||||
|         self.color = color | ||||
|         self.value = value | ||||
|  | ||||
|     def __str__(self): | ||||
|         sc = self.color if self.color else ' ' | ||||
|         sv = str(self.value) | ||||
|         return sc+' '+sv | ||||
|  | ||||
|     def __repr__(self): | ||||
|         return str(self) | ||||
|  | ||||
|  | ||||
| class Player: | ||||
|     def __init__(self, name, player_id): | ||||
|         self.name = name | ||||
|         self.id = player_id | ||||
|         self.cards = [] | ||||
|  | ||||
|     def set_cards(self, cards): | ||||
|         self.cards = cards | ||||
|  | ||||
|     def show_cards(self): | ||||
|         print(self.cards) | ||||
|  | ||||
|  | ||||
| class WizGame: | ||||
|     def __init__(self): | ||||
|         self.players = [] | ||||
|         self.card_deck = [] | ||||
|         self.trump_color = None | ||||
|  | ||||
|     def create_deck(self): | ||||
|         for color in ["b", "r", "g", "y"]: | ||||
|             for val in range(1,14): | ||||
|                 self.card_deck.append(Card(color, val)) | ||||
|         for _ in range(1,5): | ||||
|             self.card_deck.append(Card(None, 'Z')) | ||||
|         for _ in range(1,5): | ||||
|             self.card_deck.append(Card(None, 'N')) | ||||
|         print("carddeck:") | ||||
|         print(self.card_deck) | ||||
|  | ||||
|     def set_trump_color(self, card: Card): | ||||
|         if card.color: | ||||
|             self.trump_color = card.color | ||||
|         elif card.value == 'Z': | ||||
|             self.trump_color = 'choose' | ||||
|         else: | ||||
|             self.trump_color = None | ||||
|  | ||||
|     def deal_cards(self, cards_per_player): | ||||
|         random.shuffle(self.card_deck) | ||||
|         cs = list(chunks(self.card_deck, cards_per_player)) | ||||
|         for idx,p in enumerate(self.players): | ||||
|             p.set_cards(cs[idx]) | ||||
|             p.show_cards() | ||||
|         if len(cs) > len(self.players): | ||||
|             cc = cs[len(self.players)] | ||||
|             c = cc[0] | ||||
|             print("trump card: {}".format(c)) | ||||
|             self.set_trump_color(c) | ||||
|         else: | ||||
|             self.trump_color = None | ||||
|         print("trump color: {}".format(self.trump_color)) | ||||
|  | ||||
|     def add_player(self, name: str, player_id): | ||||
|         if len(self.players) < 6: | ||||
|             self.players.append((Player(name, player_id))) | ||||
|  | ||||
|  | ||||
| the_game = WizGame() | ||||
|  | ||||
		Reference in New Issue
	
	Block a user