标签:
- git clone
- 推送本地更新到repository
1) 创建新文件到master
2) 创建一个branch
$ git branch
* master
twitter_integration
$ git checkout twitter_integration app/models/avatar.rb db/migrate/20090223104419_create_avatars.rb test/unit/models/avatar_test.rb test/functional/models/avatar_test.rb
$ git status
# On branch master
# Changes to be committed:
# (use "git reset HEAD <file>..." to unstage)
#
# new file: app/models/avatar.rb
# new file: db/migrate/20090223104419_create_avatars.rb
# new file: test/functional/models/avatar_test.rb
# new file: test/unit/models/avatar_test.rb
#
$ git commit -m "‘Merge‘ avatar code from ‘twitter_integration‘ branch"
[master]: created 4d3e37b: "‘Merge‘ avatar code from ‘twitter_integration‘ branch"
4 files changed, 72 insertions(+), 0 deletions(-)
create mode 100644 app/models/avatar.rb
create mode 100644 db/migrate/20090223104419_create_avatars.rb
create mode 100644 test/functional/models/avatar_test.rb
create mode 100644 test/unit/models/avatar_test.rb
3) fork
fork的repository,在被你自己更新了之后,不会影响原owner的内容,除非原owner启动pull request
关于为什么我们需要YAML和JSON就不说了,Kirk首先介绍了为什么用YAML,主要是因为他们能处理比较复杂的data structure
在介绍YAML的时候,Kirk首先使用了list,并且展示了list的几个features,比如下面这个把一个dictionary加到列表里去 my_list.append({}), 千万注意不要把{}的两边加上quote,如果加上quote就成了一个string了
>>> import yaml
>>> my_list = range(8)
>>> my_list
[0, 1, 2, 3, 4, 5, 6, 7]
>>> my_list.append(‘whatever‘)
>>> my_list.append(‘hello‘)
>>> my_list.delete(‘{}‘) # this is not a dictionary
>>> my_list.append({})
>>> my_list[-1][‘ip_addr‘] = ‘10.10.10.239‘ # -1 means the last item of list, it‘s a dictionary, and we are here define that dictionary
>>> my_list
[0, 1, 2, 3, 4, 5, 6, 7, ‘whatever‘, ‘hello‘, ‘{}‘, {‘ip_addr‘: ‘10.10.10.239‘}]
>>> my_list[-1][‘attribs‘] = range(7)
>>> my_list
[0, 1, 2, 3, 4, 5, 6, 7, ‘whatever‘, ‘hello‘, ‘{}‘, {‘attribs‘: [0, 1, 2, 3, 4, 5, 6], ‘ip_addr‘: ‘10.10.10.239‘}]
#这个地方要注意的是,[-1]一直是那个dictionary,刚刚把range(7)放进list仅仅是放进dictionary,而不是再站一个[-1]的位置,我第一次敲这个地方#的时候理解错了
>>> type(my_list[-1]) #使用type功能看是什么数据类型
<type ‘dict‘>
- 把list转换成YAML格式
>>> yaml.dump(my_list)
"- 0\n- 1\n- 2\n- 3\n- 4\n- 5\n- 6\n- 7\n- whatever\n- hello\n- ‘{}‘\n- attribs: [0, 1, 2, 3, 4, 5, 6]\n ctest: the_second_key\n ip_addr: 10.10.10.239\n"
>>>
>>> yaml.dump(my_list, default_flow_style = True)
"[0, 1, 2, 3, 4, 5, 6, 7, whatever, hello, ‘{}‘, {attribs: [0, 1, 2, 3, 4, 5, 6], ctest: the_second_key,\n ip_addr: 10.10.10.239}]\n"
>>># 注意YAML里string两端没有quote
>>> print yaml.dump(my_list, default_flow_style = True)
[0, 1, 2, 3, 4, 5, 6, 7, whatever, hello, ‘{}‘, {attribs: [0, 1, 2, 3, 4, 5, 6], ctest: the_second_key,
ip_addr: 10.10.10.239}]
>>> print yaml.dump(my_list, default_flow_style = False) #这种更适合人类阅读
- 0
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- whatever
- hello
- ‘{}‘
- attribs:
- 0
- 1
- 2
- 3
- 4
- 5
- 6
ctest: the_second_key
ip_addr: 10.10.10.239
>>>
- 把YAML写进某YAML文件
#接着上面的来
>>> with open("some_file.yml", "w") as stream:
# 我的理解就是open一个“莫须有”的文件some_file.yml,反正他会自动创建,如果当前目录没有,用write的方式打开它,as sth,我喜欢命名成stream,因为我的理解是它就像一个stream,一串内存流一样的东西
... stream.write(yaml.dump(my_list, default_flow_style = False)) #调用这串stream的写功能,就能写进这个some_file.yml
...
>>>
- 读一个YAML文件
>>> with open("some_file.yml", ) as stream: #读刚刚那个yml文件
... new_list = yaml.load(stream)
...
>>> new_list
[0, 1, 2, 3, 4, 5, 6, 7, ‘whatever‘, ‘hello‘, ‘{}‘, {‘attribs‘: [0, 1, 2, 3, 4, 5, 6], ‘ip_addr‘: ‘10.10.10.239‘, ‘ctest‘: ‘the_second_key‘}]
>>> my_list
[0, 1, 2, 3, 4, 5, 6, 7, ‘whatever‘, ‘hello‘, ‘{}‘, {‘attribs‘: [0, 1, 2, 3, 4, 5, 6], ‘ip_addr‘: ‘10.10.10.239‘, ‘ctest‘: ‘the_second_key‘}]
>>> new_list == my_list
True #新的这个list跟老的这个完全是一样的
>>>
- JSON部分
其实和YAML很像,但是需要注意的是,json.dumps是用来读的,这里有个s,也是以string的形式读出的意思,json.dump没有s的这个是用来写的,json不接受末尾有逗号的list,哪怕是其中某个dictionary的末尾item带着一个多余的comma也不可以,虽然Python本身对于末尾有逗号的list是无所谓的
? ~ python
Python 2.7.5 (default, Mar 9 2014, 22:15:05)
[GCC 4.2.1 Compatible Apple LLVM 5.0 (clang-500.0.68)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> import json
>>> my_list = range(8)
>>> my_list.append(‘whatever‘)
>>> my_list.append(‘hello‘)
>>> my_list.append({})
>>> my_list.[-1][‘ip_addr‘] = ‘10.19.25.1‘ #注意这里的dot是不应该有的
File "<stdin>", line 1
my_list.[-1][‘ip_addr‘] = ‘10.19.25.1‘
^
SyntaxError: invalid syntax
>>> my_list[-1][‘ip_addr‘] = ‘10.19.25.1‘
>>> my_list[-1][‘attribs‘] = range(5)
>>>
>>> my_list
[0, 1, 2, 3, 4, 5, 6, 7, ‘whatever‘, ‘hello‘, {‘attribs‘: [0, 1, 2, 3, 4], ‘ip_addr‘: ‘10.19.25.1‘}]
>>>
>>> json.dumps(my_list) #注意这里是dumps,也注意下面的输出,两头有quotes
‘[0, 1, 2, 3, 4, 5, 6, 7, "whatever", "hello", {"attribs": [0, 1, 2, 3, 4], "ip_addr": "10.19.25.1"}]‘
>>>
>>> string_or_not = json.dumps(my_list) #看这个地方,说明了dumps的确是以string的形式dump出来
>>> type(string_or_not)
<type ‘str‘>
>>>
>>>
- 写和读JSON file,注意这里的dump没有s
>>> with open("my_file.json", "w") as stream:
... json.dump(my_list, stream)
...
>>>
>>> with open("my_file.json") as stream:
... new_list = json.load(stream)
...
>>> new_list
[0, 1, 2, 3, 4, 5, 6, 7, u‘whatever‘, u‘hello‘, {u‘attribs‘: [0, 1, 2, 3, 4], u‘ip_addr‘: u‘10.19.25.1‘}]
>>>
- pprint介绍
>>> from pprint import pprint as pp #这个地方也是在炫技
>>> pp(new_list)
[0,
1,
2,
3,
4,
5,
6,
7,
u‘whatever‘,
u‘hello‘,
{u‘attribs‘: [0, 1, 2, 3, 4], u‘ip_addr‘: u‘10.19.25.1‘}]
>>>
pip install 即可安装,可以处理IOS和类IOS风格的配置文本文件,它有个parent和children的概念,用于表示配置的段落和缩进
.find_objects(r”^something”) “”里是正则,所以这里有^做开头
? Desktop python
Python 2.7.5 (default, Mar 9 2014, 22:15:05)
[GCC 4.2.1 Compatible Apple LLVM 5.0 (clang-500.0.68)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> from ciscoconfparse import CiscoConfParse
>>> cisco_cfg = CiscoConfParse("test_file.txt")
>>> cisco_cfg
<CiscoConfParse: 718 lines / syntax: ios / comment delimiter: ‘!‘ / factory: False>
>>>
>>> intface = cisco_cfg.find_object(r"^interface")
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: ‘CiscoConfParse‘ object has no attribute ‘find_object‘
>>> intface = cisco_cfg.find_objects(r"^interface") # 注意是find_objects,这里有个s
>>> intface
[<IOSCfgLine # 13 ‘interface Ethernet0/0‘>, <IOSCfgLine # 20 ‘interface Ethernet0/1‘>, <IOSCfgLine # 27 ‘interface Ethernet0/1.829‘>, <IOSCfgLine # 33 ‘interface Ethernet0/1.837‘>, <IOSCfgLine # 39 ‘interface Ethernet0/2‘>, <IOSCfgLine # 42 ‘interface Ethernet0/3‘>, <IOSCfgLine # 47 ‘interface Management0/0‘>]
>>> type(intface) # type(x)真的好好用,所以每一个被抓出来的interface都是一个string
<type ‘list‘>
>>>
>>>
>>> for i in intface:
... print i.text # 必须print i.text才能打印出人看的格式,这里要说的是,i必须是这个list中的某个string,直接list是不能调用.text的,所以这里写了循环去调用
...
interface Ethernet0/0
interface Ethernet0/1
interface Ethernet0/1.829
interface Ethernet0/1.837
interface Ethernet0/2
interface Ethernet0/3
interface Management0/0
>>>
- 注意上面被抓出来的interface形成的list,他们的每个interface又是parent,所以每个parent的children又是list,如下
>>> fa3 = intface[5] #我需要先赋值,把刚刚抓出来的list的第6??个string, 也就是[5] 赋值给fa3,fa3是e0/3口
>>> fa3
<IOSCfgLine # 42 ‘interface Ethernet0/3‘>
>>>
>>>
>>> fa3.children # e0/3的children
[<IOSCfgLine # 43 ‘ no nameif‘ (parent is # 42)>, <IOSCfgLine # 44 ‘ security-level 100‘ (parent is # 42)>, <IOSCfgLine # 45 ‘ no ip address‘ (parent is # 42)>]
>>> fa3.children.text # 看这里,children也是list,不能直接调用.text,
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: ‘list‘ object has no attribute ‘text‘
>>>
>>>
>>> type(fa3.children)
<type ‘list‘>
>>> for child in fa3.children: #依然需要借助循环才可以
... print child.text
...
no nameif
security-level 100
no ip address
>>>
- string_somthing.all_children 注意打印出来的也是list,我们找一个有孙子辈儿缩进的配置段落,就用global-policy吧
>>> global_policy = cisco_cfg.find_objects(r"^policy-map global_policy")
>>> global_policy
[<IOSCfgLine # 703 ‘policy-map global_policy‘>]
>>> str_global_policy = global_policy[0]
>>> str_global_policy.text
‘policy-map global_policy‘
>>> str_global_policy.all_children
[<IOSCfgLine # 704 ‘ class by-pass‘ (parent is # 703)>, <IOSCfgLine # 705 ‘ set connection advanced-options tcp-state-bypass‘ (parent is # 704)>, <IOSCfgLine # 706 ‘ class inspection_default‘ (parent is # 703)>, <IOSCfgLine # 707 ‘ inspect ftp ‘ (parent is # 706)>, <IOSCfgLine # 708 ‘ inspect icmp ‘ (parent is # 706)>, <IOSCfgLine # 709 ‘ inspect icmp error ‘ (parent is # 706)>]
>>>
>>> for child in str_global_policy.all_children:
... print child.text
...
class by-pass # 儿子辈儿
set connection advanced-options tcp-state-bypass #孙子辈儿
class inspection_default
inspect ftp
inspect icmp
inspect icmp error
>>>
- str_somthing.is_child or .is_parent 这个内置的功能是方便检查一个string是不是child或者parent
比如下面的这个class by-pass既是parent也是child
>>> from pprint import pprint as pp #这里用了pprint,还是很好用的,起码给分个行
>>> pp (str_global_policy.all_children)
[<IOSCfgLine # 704 ‘ class by-pass‘ (parent is # 703)>,
<IOSCfgLine # 705 ‘ set connection advanced-options tcp-state-bypass‘ (parent is # 704)>,
<IOSCfgLine # 706 ‘ class inspection_default‘ (parent is # 703)>,
<IOSCfgLine # 707 ‘ inspect ftp ‘ (parent is # 706)>,
<IOSCfgLine # 708 ‘ inspect icmp ‘ (parent is # 706)>,
<IOSCfgLine # 709 ‘ inspect icmp error ‘ (parent is # 706)>]
>>>
>>> str_test = str_global_policy.all_children[0]
>>> pp (str_test)
<IOSCfgLine # 704 ‘ class by-pass‘ (parent is # 703)>
>>> str_test.is_child
True
>>> str_test.is_parent
True
>>>
- .all_parents 就是把父亲辈和爷爷辈儿的都打印出来
>>> str_test.all_parents
[<IOSCfgLine # 703 ‘policy-map global_policy‘>]
>>>
>>>
>>> str_test2 = str_global_policy.all_children[-1]
>>> str_test2.all_parents
[<IOSCfgLine # 703 ‘policy-map global_policy‘>, <IOSCfgLine # 706 ‘ class inspection_default‘ (parent is # 703)>]
>>>
>>> pp (str_test2.all_parents)
[<IOSCfgLine # 703 ‘policy-map global_policy‘>,
<IOSCfgLine # 706 ‘ class inspection_default‘ (parent is # 703)>]
>>>
- .find_objects_w_child(parentspec=r”^something”, childspec=r”something”) 只搜索特定的parent和child
>>> cisco_cfg.find_objects_w_child(parentspec=r"policy-map", childspec=r"inspection_default")
[<IOSCfgLine # 703 ‘policy-map global_policy‘>]
>>>
- 当然ciscoconfparse这货也可以处理cisco风格的其他类型的输出,比如下面这段show interface
>>> show_int = CiscoConfParse("hkg_vpn_router_show_int.txt")
>>> show_int
<CiscoConfParse: 309 lines / syntax: ios / comment delimiter: ‘!‘ / factory: False>
>>>
>>> int_status = show_int.find_objects(r"^line protocol is") # 这里不应该用^作为regex的开头,因为这里是正则
>>> pp (int_status)
[]
>>> int_status = show_int.find_objects(r"line protocol is") # 不带^才能找到
>>> pp (int_status)
[<IOSCfgLine # 1 ‘GigabitEthernet0/0 is up, line protocol is up ‘>,
<IOSCfgLine # 30 ‘GigabitEthernet0/1 is up, line protocol is up ‘>,
<IOSCfgLine # 59 ‘GigabitEthernet0/2 is down, line protocol is down ‘>,
<IOSCfgLine # 86 ‘Loopback0 is up, line protocol is up ‘>,
<IOSCfgLine # 106 ‘Loopback1 is up, line protocol is up ‘>,
<IOSCfgLine # 126 ‘Tunnel17 is up, line protocol is down ‘>,
<IOSCfgLine # 157 ‘Tunnel38 is up, line protocol is down ‘>,
<IOSCfgLine # 188 ‘Tunnel102 is up, line protocol is up ‘>,
<IOSCfgLine # 219 ‘Tunnel103 is up, line protocol is up ‘>,
<IOSCfgLine # 250 ‘Tunnel200 is up, line protocol is up ‘>,
<IOSCfgLine # 279 ‘Tunnel201 is up, line protocol is up ‘>]
>>> for int in int_status:
... print int.text
...
GigabitEthernet0/0 is up, line protocol is up
GigabitEthernet0/1 is up, line protocol is up
GigabitEthernet0/2 is down, line protocol is down
Loopback0 is up, line protocol is up
Loopback1 is up, line protocol is up
Tunnel17 is up, line protocol is down
Tunnel38 is up, line protocol is down
Tunnel102 is up, line protocol is up
Tunnel103 is up, line protocol is up
Tunnel200 is up, line protocol is up
Tunnel201 is up, line protocol is up
>>> int_status[2]
>>> for i in int_status[2].children:
... print i.text
...
Hardware is BCM1250 Internal MAC, address is 0017.0f40.7819 (bia 0017.0f40.7819)
MTU 1500 bytes, BW 1000000 Kbit/sec, DLY 10 usec,
Encapsulation ARPA, loopback not set
Keepalive set (10 sec)
Auto-duplex, Auto Speed, media type is RJ45
output flow-control is XON, input flow-control is XON
ARP type: ARPA, ARP Timeout 04:00:00
Last input never, output never, output hang never
Last clearing of "show interface" counters never
Input queue: 0/75/0/0 (size/max/drops/flushes); Total output drops: 0
Queueing strategy: fifo
Output queue: 0/40 (size/max)
5 minute input rate 0 bits/sec, 0 packets/sec
5 minute output rate 0 bits/sec, 0 packets/sec
>>># quite useful
>>>
标签:
原文地址:http://www.cnblogs.com/Vooom/p/5744475.html